Re[8]: Preobrozovanie char
От: folk Россия  
Дата: 20.03.04 05:34
Оценка:
Здравствуйте, ArtDenis, Вы писали:

AD>Да, ладно, я же просто пошутил. А если говорить серьёзно, то мне не понятно, почему в C++ и C нет средства для преобразования чисел в строковое представление, которое бы удовлетворяло следующим условиям:


AD>1. Безопасность и надёжность

AD>2. Выбор формата чисел
AD>3. Высокая скорость
AD>4. Маленький объём кода

AD>Если построить таблицу по функциям переводящим double -> text и по вышеприведённым условиям, то получим:


AD>
AD>Средство            |  1    2    3    4
AD>====================+=====================
AD>sprintf             |  -    +    +    +
AD>------------------------------------------
AD>gcvt, ecvt, fcvt    |  -    -    +    +
AD>------------------------------------------
AD>stringstream        |  +    +    -    -
AD>------------------------------------------
AD>boost::lexical_cast |  +    -    -    - 
AD>------------------------------------------
AD>


AD>Как видно, четырёх плюсов подряд нигде не наблюдаеся


Я тоже как-то думал над этим. И тоже пришел к выводу что в стандартных C/C++ нет удобного способа пребразования значения в строковое представление. А альтернативные удобные способы достаточно дорогие.

Мне хочется иметь набор перегруженных шаблонов функций, возвращающих итератор на конец строкового представления, конечно же без зачастую ненужного нуль-терминирования. Все параметры форматирования должны паковаться в спец тип вместе с форматируемым значением.
Типа такого на примере signed/unsigned int и дополнительного шестнацатиричного формата:

// шестнадцатиричный форматтер - может использоваться с любыми семантически подходящими типами
template<typename T>
struct hex_t
{
  T value;
  explicit hex_t(T val): value(val) {}
};

template<typename T>
hex_t<T> hex(T const& val) { return hex_t<T>(val); }

// объявления шаблонов преобразования
tempalte<typename OutIt>
OutIt stringize(OutIt it, unsigned x);

tempalte<typename OutIt>
OutIt stringize(OutIt it, signed x);

tempalte<typename OutIt>
OutIt stringize(OutIt it, hex_t<unsigned> x);

tempalte<typename OutIt>
OutIt stringize(OutIt it, hex_t<signed> x);

// здесь мы несколько выбиваемся из стиля, но должнен же быть шаблон для удобной работы с массивом символов,
// терминирующий нулем и возвращающий указатель на НАЧАЛО массива
template<typename Char, typename T>
Char* stringize_to_array(Char* buf, T const& x)
{
  *stringize(buf, x) = 0;
  return buf;
}


Такие шаблоны было бы весьма удобно использовать в различных ситуациях. Вот напридумывал примеры использования:

void test()
{
  std::string s;
  stringize(std::back_inserter(s), hex(12345));

  stringize(std::ostreambuf_iterator<wchar_t>(std::wcout), 12345);

  char buf[32];
  std::cout << stringize_to_array(buf, 12345);
}


ЗЫ Для целых чисел это сделать совсем несложно, да и вариантов формата для них немного. А вот с плавающими числами все сложнее.
На самом деле, люди не читают газеты, они принимают их каждое утро, так же как ванну. ©Маршалл Мак-Льюэн
Re: Preobrozovanie char
От: marat321  
Дата: 20.10.05 08:50
Оценка:
Здравствуйте, <Аноним>, Вы писали:

Почему нельзя использовать std::string и в нее писать через потоки, а потом выдрать указатель на char?
... << RSDN@Home 1.1.4 stable SR1 rev. 568>>
Re[5]: Preobrozovanie char
От: Pavel Chikulaev Россия  
Дата: 21.10.05 08:37
Оценка:
Здравствуйте, Шахтер, Вы писали:

Ш>Не надо путать программирование и идиотию. Авторы boost а, во всяком случае этой его части, программистами названы быть не могут. Ими вообще должны заниматься специальные люди в былых халатах.


Кстати велика вероятность, что boost::lexical_cast будет в C++0x. Так что привыкай.
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.