Jaki jest najlepszy sposób konwersji std :: string na bool? Wywołuję funkcję, która zwraca wartość "0" lub "1", i potrzebuję czystego rozwiązania do przekształcenia tego w wartość boolowską.Konwersja z std :: string na bool
Odpowiedz
To będzie prawdopodobnie overkill dla ciebie, ale użyję boost::lexical_cast
boost::lexical_cast<bool>("1") // returns true
boost::lexical_cast<bool>("0") // returns false
bool to_bool(std::string const& s) {
return s != "0";
}
Napisz bezpłatną funkcję:
bool ToBool(const std::string & s) {
return s.at(0) == '1';
}
Chodzi o najprostszej rzeczy, które mogą działać, ale trzeba zadać sobie pytanie:
- co powinno pusty zwrot ciąg? powyższa wersja zgłasza wyjątek:
- do czego powinien się skonwertować znak inny niż "1" lub "0"?
- to ciąg znaków składający się z więcej niż jednego znaku, ważnego wejścia dla funkcji?
Jestem pewien, że są inni - to jest radość z projektowania interfejsu API!
To najlepsza metoda, jak sądzę. Używanie 'at' jako czeku jest bardzo czyste. – GManNickG
@GMan: Nie jestem pewien, czy się z tym zgadzam. W C 0 oznacza fałsz, a wszystko inne jest prawdziwe. Zatem 2 jest prawdziwe, 03 jest prawdziwe, itd. Tak więc, chociaż pytanie jest niedookreślone, rozsądnie jest założyć, że wszystko, co nie jest zerem, jest prawdziwe. –
@Chris Jak o "00"? Mój punkt widzenia w tej odpowiedzi brzmiał, że nawet w przypadku tak prostej funkcji, istnieje wiele problemów, które należy zbadać. –
Spróbuj tego:
bool value;
if(string == "1")
value = true;
else if(string == "0")
value = false;
bool to_bool(std::string const &string) {
return string[0] == '1';
}
bym zmienić brzydkie funkcję zwracającą ten ciąg w pierwszej kolejności. Po to jest bool.
Nie mam kontroli nad tą funkcją, jest to biblioteka strony trzeciej. – cquillen
Biblioteka wydaje się jednak trochę głupia. Czy istnieje jakikolwiek powód, dla którego powinien on używać 'std :: string' ze wszystkich rzeczy dla powrotu boolowskiego? – UncleBens
@UncleBens - może używa std :: string jako typu "wariant". –
oto sposób podobny do Kyle'a oprócz tego, że obsługuje zer i rzeczy:
bool to_bool(std::string const& s) {
return atoi(s.c_str());
}
Ale ale ale ... "DEADBEEF" będzie traktowany jako fałszywy! :-P –
A dlaczego miałaby to być prawda? –
@Andreas: Tradycją C jest to, że 0 jest fałszywe, a wszystko inne jest prawdą. Idealnie chciałbym rzucić wyjątek w tym przypadku, ale jeśli to nie jest opcja, to prawda jest "mniej błędna" niż fałszywa, według mnie. –
I d używaj tego, co robi, co chcesz, i łapie przypadek błędu.
bool to_bool(const std::string& x) {
assert(x == "0" || x == "1");
return x == "1";
}
Zawsze możesz owinąć zwrócony ciąg w klasie, która obsługuje koncepcję logicznych ciągów:
class BoolString : public string
{
public:
BoolString(string const &s)
: string(s)
{
if (s != "0" && s != "1")
{
throw invalid_argument(s);
}
}
operator bool()
{
return *this == "1";
}
}
połączeń coś takiego:
BoolString bs(func_that_returns_string());
if (bs) ...;
else ...;
Która rzuci invalid_argument
jeśli reguła dotycząca "0"
i "1"
jest naruszona.
Nie wszystko musi być klasą; bezpłatna funkcja jest znacznie czystsza i bezpieczniejsza. – GManNickG
@GMan, byłbym pierwszy, który to powiedziałby :) –
Albo zależy Ci na możliwości uzyskania nieprawidłowej wartości zwrotu, albo nie. Większość dotychczasowych odpowiedzi znajduje się w środkowej części, chwytając kilka ciągów poza "0" i "1", być może racjonalizując, jak powinny zostać przekształcone, być może rzucając wyjątek. Nieprawidłowe dane wejściowe nie mogą wygenerować prawidłowych danych wyjściowych i nie należy ich akceptować.
Jeśli nie zależy Ci na nieprawidłowych zwrotach, użyj s[0] == '1'
. To bardzo proste i oczywiste. Jeśli musisz uzasadnić swoją tolerancję wobec kogoś, powiedz, że konwertuje niepoprawne dane wejściowe na fałsz, a pusty łańcuch prawdopodobnie będzie pojedynczym \0
w implementacji STL, więc jest dość stabilny. s == "1"
jest również dobry, ale s != "0"
wydaje mi się dla mnie rozwlekły i sprawia, że jest on nieprawidłowy => true.
Jeżeli dbam o błędach (i prawdopodobnie powinno), użyj
if (s.size() != 1
|| s[0] < '0' || s[0] > '1') throw input_exception();
b = (s[0] == '1');
Ten łapie wszystkie błędy, ale także wprost oczywiste i proste dla każdego, kto zna smidgen C, i nic nie będzie wykonywać szybciej .
Dziwię się, że nikt nie wspomniał o tym jednym:
bool b;
istringstream("1") >> b;
lub
bool b;
istringstream("true") >> std::boolalpha >> b;
Reputacja nie zawsze idzie w parze z odpowiedzią (imho). :) – gsamaras
Nice! To działało dla mnie przy użyciu interfejsu Lua C API.Przypuszczam, że C nie ma typu danych boolean ; lua_toboolean() zwraca wartość int 0 lub 1, więc wydaje się, że działa to w C++. – Artorias2718
Tak, to strumienie C++ https://www.cprogramming.com/tutorial/c++-iostreams.html. –
Istnieje również std :: Stoi w C++ 11:
wartość bool = std :: stoi (someString.c_str());
- 1. Konwersja std :: __ cxx11 :: string na std :: string
- 2. Konwersja uint64_t na std :: string
- 3. konwersja int na std :: string
- 4. Preferowana konwersja z char (nie char *) na std :: string
- 5. Przeciążenie Bool/String Niejednoznaczność
- 6. Konwersja int na bool z Json.NET
- 7. Konwersja boost :: opcjonalna na bool
- 8. std :: string na LPCTSTR
- 9. Konwersja String na krótki
- 10. Konwersja String na NSDecimalNumber
- 11. konwersja z nullptr_t na bool: poprawny czy nie?
- 12. automatyczna konwersja bool do nullptr_t
- 13. Niejednoznaczne wywołanie (konwersja z char * do lambda vs std :: string)
- 14. Sortowanie std :: wektor <std :: pair <std :: string, bool >> według ciągu znaków?
- 15. Dlaczego niejawna konwersja Bool na ciąg nie jest błędem?
- 16. Różnica między std: string i std :: string
- 17. Konwersja std :: array na std :: vector
- 18. doładowanie :: ifind_first z std :: string objects
- 19. Konwersja String na typ Konstruktora w Haskell
- 20. Python: Konwersja z Tuple na String?
- 21. Konwersja Boolean na String z Inno Setup
- 22. Konwersja z struct timespec na std :: chrono ::?
- 23. Konwersja std :: wstepna na char * z wcstombs_s
- 24. Konwersja std :: wstring na int
- 25. Konwersja String na tablicę znaków
- 26. Konwersja String na obiekt dynamiczny
- 27. Nie powinien char * niejawnie przekonwertować na std :: string?
- 28. C++ niejawna konwersja do bool
- 29. Konwersja std :: para iteratorów na boost :: iterator_range
- 30. Interakcja Rust z C++ std :: string
Ponieważ to rozwiązanie obejmuje pewien narzut, nie należy go używać, gdy wydajność jest ważna. Lub wyspecjalizuj boost :: leksykalny dla własnych potrzeb. – smerlin
Jeśli możesz pozwolić sobie na konwersję łańcuchów na sygnały ... W każdym razie +1: to jak dotąd najsolidniejsza metoda. A jeśli okaże się zbyt powolny, czy nie byłoby możliwe specjalizację leksykalnej_przekładki/błagać ludzi doładowania, aby to zrobili? :) –
UncleBens
Jak to jest bardziej niezawodne niż cokolwiek innego? Jego zachowanie jest niejasne, na przykład przypadkowe niezerowe liczby stają się prawdziwe, "prawda", a pusty ciąg powinien generować wyjątki. (Nie wiem od ręki). – Potatoswatter