Strumienie wyjściowe obsługują formatowanie wyjściowe oraz wyjście. Tak ze swoimi toString()
klientów metoda nie będzie w stanie zarządzać formatowanie dla obiektu tak robią wszystkiego innego:
// set specific formatting options for printing a value
std::cout << std::scientific << std::setprecision(10) << 10.0 << '\n'; // prints 1.0000000000e+01
// set formatting based on user's cultural conventions
std::cout.imbue(std::locale(""));
std::cout << 10000000 << '\n'; // depending on your system configuration may print "10,000,000"
Być może nie obchodzi, aby umożliwić dowolne formatowanie, więc być może to nie będzie miało znaczenia, .
Innym zagadnieniem jest to, że wyjście do strumienia nie wymaga, aby cała reprezentacja ciągów znajdowała się w pamięci naraz, ale metoda toString()
to robi.
inni zwrócili na to uwagę, ale myślę, że wyraźniejszy sposób, mówiąc, że jest to, że interfejs klasy nie jest ograniczone tylko do metod to świadczy, ale zawiera także inne funkcje, zbudować wokół niego, w tym niekonwencjonalnych - funkcje potomne, takie jak przeciążenia, które zapewniasz, operator<<
. Nawet jeśli nie jest to metoda twojej klasy, powinieneś myśleć o niej jako o interfejsie twojej klasy.
Oto artykuł, który mówi o tym, które być może znajdziesz pomocne: How Non-Member Functions Improve Encapsulation
Oto prosty przykład przeciążenia operator<<
przez użytkownika określonej klasie:
#include <iostream>
struct MyClass {
int n;
};
std::ostream &operator<< (std::ostream &os, MyClass const &m) {
for (int i = 0; i < m.n; ++i) {
os << i << ' ';
}
return os;
}
int main() {
MyClass c = {1000000};
std::cout << c << '\n';
}
Jak to zrobić dla 'int'? Czy masz na myśli 'to_string'? – doctorlove
Ponieważ tworzenie czegoś, co można przesyłać strumieniowo, nie jest tym samym, co przekształcenie go w ciąg znaków. Jeśli chcesz, aby Twój typ mógł być przesyłany strumieniowo, należy przeładować 'ostream & operator <<'. Jeśli chcesz tworzyć z niego łańcuchy, daj mu to_string member. – juanchopanza