Два глупых вопроса по STL.
Во-первых, почему ostream::write принимает char*, а не void*? Кастить парит.немного ошибаешься
// 27.6.2.6 Unformatted output:я думаю, это все объясняет
basic_ostream<charT,traits>& put(char_type c);
basic_ostream<charT,traits>& write(const char_type* s, streamsize n);
Во-вторых, как можно при помощи алгоритма copy вывести set<int> в бинарный файл (в бинарном же виде)?поподробнее плиз опиши задачу. что вы ожидаете от этого вывода? будете ли вы читать потом это?
Во-вторых, как можно при помощи алгоритма copy вывести set<int> в бинарный файл (в бинарном же виде)?Вам не должно этого хотеться так.
Во-вторых, как можно при помощи алгоритма copy вывести set<int> в бинарный файл (в бинарном же виде)?Свой output iterator написать. Можно посмотреть на ostream_iterator и сделать по образу и подобию.
Свой output iterator написать. Можно посмотреть на ostream_iterator и сделать по образу и подобию.итераторы вроде не занимаются форматированием вывода. этим заведуют всякие facet, ctype, traits, etc
в общем, тоже не считаю это хорошей затеей
лучше освойте сериализацию другими методами
итераторы вроде не занимаются форматированием вывода.Если в итератор можно засунуть вызов write то почему бы так и не сделать? Полностью же по аналогии с back_insert_iterator и ostream_iterator будет.
этим заведуют всякие facet, ctype, traits, etcКак с помощью всего этого решить задачу вывода последовательности в двоичном виде в ofstream через std::copy?
итераторы вроде не занимаются форматированием вывода. этим заведуют всякие facet, ctype, traits, etcНу естественно, итераторы этим не занимаются, они итерируют
Но вот ostream_iterator пользуется <<, хочется воспользоваться вместо него .write'ом. Хотелось стандартного решения, свой итератор написать — более-менее решение, а вот хотелось знать, как без лишней писанины.я думаю, это все объясняетну мооожет быть, но все равно, write'ом, кмк, чаще выводят raw data, чем отформатированный заранее текст. Ну да пох.
как без лишней писанины.Не тот язык выбрал

я не против пописать там, где это нужно, но здесь вот форматированный вывод можно сделать, а бинарный — на первый взгляд нет.
Короче гугли по словам c++ ser1al1zat10n, увидишь, какие кактусы вырастают на почве невинных желаний типа твоего из первого п0ста.
---
Ч0рт0вb1 теHдepы на г0C3аkyпкN съеJIи M0CK
---
Ч0рт0вb1 теHдepы на г0C3аkyпкN съеJIи M0CK

Фишка в том, что мне не надо сериализовать set, мне надо сохранить числа из него подряд в файл, там формат фиксирован внешними факторами.
Я бы написала библиотечкку для работы с файлами этого формата, и юзал бы её.
да я бы тоже написала, но слишком обобщенную ее писать лень (а по задаче придется). Да и не в этом дело, просто до этого не так много опыта с STL'ем было, вот и ищу правильные пути.
> да я бы тоже написала, но слишком обобщенную ее писать лень (а по задаче придется). Да и не в этом дело, просто до этого не так много опыта с STL'ем было, вот и ищу правильные пути.
> STL'ем ... правильные пути
> пути
"
В пути я занемог.
И все бежит, кружит мой сон
По выжженным полям.
"
"
Сказали мне, что эта дорога меня приведёт к океану смерти,
И я с полпути повернула вспять.
С тех пор все тянутся предо мною кривые, глухие окольные тропы…
"
> STL'ем ... правильные пути
> пути
"
В пути я занемог.
И все бежит, кружит мой сон
По выжженным полям.
"
"
Сказали мне, что эта дорога меня приведёт к океану смерти,
И я с полпути повернула вспять.
С тех пор все тянутся предо мною кривые, глухие окольные тропы…
"
Во-первых, почему ostream::write принимает char*, а не void*? Кастить парит.а что такое void*?
указатель? зачем указатель выводить в поток?
char* - это бинарные данные, их в поток и надо выводить
ещё лучше если бы это называлось byte*, тогда бы таких вопросов не было бы
почему void* не бинарные данные?
ну хотя бы потому что sizeof(void) не определён
Фишка в том, что мне не надо сериализовать set, мне надо сохранить числа из него подряд в файл, там формат фиксирован внешними факторами.зачем тебе при этом std::copy?
Потому что в форматированном виде я могу вывести (через ostream_iterator почему я не должен хотеть сделать это в бинарном виде?
а что такое void*?йоу, мэн! Ты чего? Указатель указывает на данные, которые мне надо записать в поток. void* — это указатель на что угодно, см. функцию memcpy, например.
указатель? зачем указатель выводить в поток?
char* - это бинарные данные, их в поток и надо выводитьДа char и byte и так в голове синонимы (для c/c++ так что это неважно, но вот это про sizeof(void) — что-то неясное.
ещё лучше если бы это называлось byte*, тогда бы таких вопросов не было бы.
почему void* не бинарные данные?
ну хотя бы потому что sizeof(void) не определён
Это все не похоже на идеологическую причину, скорее это артефакт дизайна, потому что в том же C все-таки принято (хотя может и не всеми) указатель на сырые данные представлять в виде void*. См. memcpy, MPI_Send и др.
>Это все не похоже на идеологическую причину, скорее это артефакт дизайна, потому что в том же C все-таки принято (хотя может и не всеми) указатель на сырые данные представлять в виде void*. См. memcpy, MPI_Send и др.
в C - есть понятие "сырые данные" и активно используется
а в C++ - считается, что "сырые данные" - это зло, и стараются это понятие не использовать
в C - есть понятие "сырые данные" и активно используется
а в C++ - считается, что "сырые данные" - это зло, и стараются это понятие не использовать
На stackoverflow нашел идею достаточно лаконичного решения:
#include <iostream>
#include <iterator>
#include <sstream>
#include <set>
#include <algorithm>
#include <cstdlib>
template<class T>
struct serialize
{
serialize(const T & i_value = T : value(i_value) {}
operator T const {
return value;
}
T value;
};
template<class T>
std::ostream& operator <<(std::ostream &os, const serialize<T>& obj)
{
os.writechar*)&obj.value, sizeof(T;
return os;
}
template<class T>
std::istream& operator >>(std::istream &is, serialize<T> & obj)
{
is.readchar*)&obj.value, sizeof(T;
return is;
}
int main {
std::set<int> s, s1;
generate_n(std::inserter(s, s.end 20, std::rand);
std::stringstream ios;
typedef std::ostream_iterator< serialize<int> > OutputIterator;
typedef std::istream_iterator< serialize<int> > InputIterator;
std::copy(s.begin s.end OutputIterator(ios;
std::copy(InputIterator(ios InputIterator std::inserter(s1, s1.end;
if (s == s1) {
std::cout << "OK" << std::endl;
} else {
std::cout << "Fail" << std::endl;
}
return 0 ;
}
Это было предложено уже здесь. Но спасибо за возможность увидеть объем.
Я в итоге закопировал в вектор, а его потом заврайтил в один вызов. Там не более 50-ти элементов, так что пох.
Я в итоге закопировал в вектор, а его потом заврайтил в один вызов. Там не более 50-ти элементов, так что пох.
Оставить комментарий
Serab
Во-первых, почему ostream::write принимает char*, а не void*? Кастить парит.Во-вторых, как можно при помощи алгоритма copy вывести set<int> в бинарный файл (в бинарном же виде)?