C vs. C++ (Концепция итераторов в C++, STL и т.д.)

Модератор: Модераторы разделов

sergio
Сообщения: 436
Статус: Интересующийся новичок
ОС: Debian GNU/Linux 4 & 5

Re: C vs. C++

Сообщение sergio »

v04bvs писал(а):
21.11.2007 17:06
sergio писал(а):
21.11.2007 16:08
Расскажите пожалуйста, в каком ЯВУ итераторы являются "программой организации циклов"?

Java: для использования foreach необходимо, чтобы класс имел метод iterator(), т.е. итераторы и циклы связаны как нельзя более тесно.

Они и в СИ++ связаны тесно. И даже в си. Если мы наращиваем в цикле указатель на элементы массива - указатель является итератором, точно таким же как аналогичный указатель или объект-итератор в си++. Так что и си, и си++ тогда соответствуют этому определению итераторов - они тесно связаны с циклами (но не обязательно циклы - с ними). А вот товарисч хочет нас убедить, что нет. Так что с этой стороны вы ничего не добавили, это все уже говорили выше. А вот где в вашем посте слово "программа организации циклов", которой являются итераторы - я что-то не увидел. И не заметил, чтобы итераторы организовывали цикл - все же "для использования foreach необходимо, чтобы класс имел метод iterator", а не наоборот. Ну так и в си++ для foreach нужны iterator. Да и циклы в яве не обязательно foreach, и без метода .iterator бывают, не так ли? Так что курица с яйцом местами меняются. :happy:

Диспут-то терминологический. Товарисч утверждает, что итераторы в си++ бредовы, потому что не соответствуют его пониманию итераторов и якобы не соотв-т найденному толкованию слова iterator. Вот именно толкование выглядит бредовым и ничего не доказывающим для меня. Вы пока ничего не опровергли. Ни бредовость итераторов, ни бредовость определения, ни "программу организации" не показали. :happy:

И еще, сдается мне, что диспут стал уже совсем ни о чем. )))
Debian GNU/Linux 4 -- AMD Athlon64 3000+ / Asus 7600GS -- Gnome
Debian GNU/Linux 5 -- Dell (Vostro) 500 (Celeron M560 / iGM965) -- Gnome
Спасибо сказали:
v04bvs
Сообщения: 636
ОС: Debian GNU/Linux

Re: C vs. C++

Сообщение v04bvs »

sergio писал(а):
21.11.2007 17:44
v04bvs писал(а):
21.11.2007 17:06
sergio писал(а):
21.11.2007 16:08
Расскажите пожалуйста, в каком ЯВУ итераторы являются "программой организации циклов"?

Java: для использования foreach необходимо, чтобы класс имел метод iterator(), т.е. итераторы и циклы связаны как нельзя более тесно.

Они и в СИ++ связаны тесно. И даже в си. Если мы наращиваем в цикле указатель на элементы массива - указатель является итератором, точно таким же как аналогичный указатель или объект-итератор в си++. Так что и си, и си++ тогда соответствуют этому определению итераторов - они тесно связаны с циклами (но не обязательно циклы - с ними). А вот товарисч хочет нас убедить, что нет. Так что с этой стороны вы ничего не добавили, это все уже говорили выше. А вот где в вашем посте слово "программа организации циклов", которой являются итераторы - я что-то не увидел. И не заметил, чтобы итераторы организовывали цикл - все же "для использования foreach необходимо, чтобы класс имел метод iterator", а не наоборот. Ну так и в си++ для foreach нужны iterator. Да и циклы в яве не обязательно foreach, и без метода .iterator бывают, не так ли? Так что курица с яйцом местами меняются. :happy:

Диспут-то терминологический. Товарисч утверждает, что итераторы в си++ бредовы, потому что не соответствуют его пониманию итераторов и якобы не соотв-т найденному толкованию слова iterator. Вот именно толкование выглядит бредовым и ничего не доказывающим для меня. Вы пока ничего не опровергли. Ни бредовость итераторов, ни бредовость определения, ни "программу организации" не показали. :happy:

И еще, сдается мне, что диспут стал уже совсем ни о чем. )))

Мне итераторы не нравятся потому, что без автовывода типов строка "for (std::vector<int>::const_iterator i = a.begin(); i != a.end(); ++i)" выглядит абсолюто дико и не читаемо. И потому, что нельзя реализовать настоящий std::remove_if например. У меня лично претензий больше нет :)
Спасибо сказали:
sergio
Сообщения: 436
Статус: Интересующийся новичок
ОС: Debian GNU/Linux 4 & 5

Re: C vs. C++

Сообщение sergio »

v04bvs писал(а):
21.11.2007 18:03
Мне итераторы не нравятся потому, что без автовывода типов строка "for (std::vector<int>::const_iterator i = a.begin(); i != a.end(); ++i)" выглядит абсолюто дико и не читаемо. И потому, что нельзя реализовать настоящий std::remove_if например. У меня лично претензий больше нет :)

О! как доходит до кода, так совсем другое дело и все понятно. :happy:
Такой шаблон читается имхо еще сносно. А если больше одного, там сам бог велел typedef-ить его. )) Набирать - да, долго. ))) Кстати, тута были товарисчи, любившие вим с емаксом - может они поделятся наработками по сокращению набора в таких случаях? ))))) Все же имхо быстрый набор важен для шелл, а для плюсов тут ИДЕ или редактору не грех и помочь...

Ждем watashiwa_daredeska с примерами кода, где правильные итераторы хороши, а неправильные плохи. ))
Debian GNU/Linux 4 -- AMD Athlon64 3000+ / Asus 7600GS -- Gnome
Debian GNU/Linux 5 -- Dell (Vostro) 500 (Celeron M560 / iGM965) -- Gnome
Спасибо сказали:
watashiwa_daredeska
Бывший модератор
Сообщения: 4038
Статус: Искусственный интеллект (pre-alpha)
ОС: Debian GNU/Linux

Re: C vs. C++

Сообщение watashiwa_daredeska »

sergio писал(а):
21.11.2007 16:08
То, что вы привели - это не значение слова, а узкоспециальная трактовка слова, его толкование, выполненное неизвестным мне специалистом.

То же самое я могу сказать и про ваш вариант. Но это совсем другая проблема -- описание смысла слова на другом языке. Так что, не будем больше об этом.

Ваш вариант трактовки:
(sergio) писал(а):Итератор - это повторитель, перебиратель. Поинтер, способный указывать на очередной элемент множества и сдвигаться на следующий элемент того же множества, или быть принудительно связан с любым другим.

Отличается не так уж сильно. Я позволил себе выделить в цитате место, которое, на мой взгляд, к повторению и перебору не имеет никакого отношения.

На самом деле, проблема итераторов C++ именно в их перегруженности функционалом. В результате, в C++ цель получить "итератор вообще" не достигнута, зато разведен бардак с кучей итераторов, обладающих разными возможностями.

sergio писал(а):
21.11.2007 16:08
Вы бы рассказали, под какую ситуацию вам чего не хватает, почему там плюсовые недоитераторы плохи, и как вы это предлагает решать с "правильными итераторами".

Поясняю еще раз:
watashiwa_darede... писал(а):
21.11.2007 11:15
что-то вроде шелловского: command | grep pattern | sort | uniq.

но для объектов. Еще бы аналог tee не помешал. Если интересно, могу продемонстрировать решение этой задачки для, например, Python, но в отдельной ветке -- создайте, если вам действительно интересно.

sergio писал(а):
21.11.2007 16:08
Итератор - поинтер на элемент некой произвольно упорядоченной последовательности, обеспечивает косвенный доступ элементу, может быть перемещен на другой элемент или на мнимый элемент за концом. Для N числа элементов как-либо упорядоченных в последовательность, может быть одновременно задано и недеструктивно использовано (N + 1)! различных (под-)последовательностей, заданных соответствующим количеством пар итераторов одного типа.

Вот-вот. Проблема C++-итераторов как раз в том, что они -- "пойнтер". По хорошему, итератор -- это НЕ пойнтер.

Про "недеструктивно использовано" и "(N+1)!" не понял, если честно.

sergio писал(а):
21.11.2007 16:08
Расскажите пожалуйста, как подобная гибкость достигается якобы-правильными итераторами?

За счет простоты создания производных итераторов достигается гораздо большая гибкость. Нафига мне какой-то мифический (N+1)! последовательностей? Мне нужны вполне определенные: скажем, итератор обхода дерева в ширину, итератор обхода дерева в глубину (которых, как и деревьев, к слову, в std нет), и простые, но гибкие способы создания производных итераторов.
Спасибо сказали:
Аватара пользователя
serzh-z
Бывший модератор
Сообщения: 8259
Статус: Маньяк
ОС: Arch, Fedora, Ubuntu

Re: C vs. C++

Сообщение serzh-z »

watashiwa_darede... писал(а):
21.11.2007 18:41
На самом деле, проблема итераторов C++ именно в их перегруженности функционалом.
Функционалом? Это где же?

watashiwa_darede... писал(а):
21.11.2007 18:41
но для объектов. Еще бы аналог tee не помешал.
Не вижу проблемы в том, чтобы создать свой класс, скажем tee, который примет в конструктор два итератора (begin и end) для чтения, и два итератора (begin1, begin2) дла записи...
Спасибо сказали:
sergio
Сообщения: 436
Статус: Интересующийся новичок
ОС: Debian GNU/Linux 4 & 5

Re: C vs. C++

Сообщение sergio »

watashiwa_daredeska писал(а):
21.11.2007 18:41
То же самое я могу сказать и про ваш вариант. Но это совсем другая проблема -- описание смысла слова на другом языке. Так что, не будем больше об этом.
Ваш вариант трактовки:
(sergio) писал(а):Итератор - это повторитель, перебиратель. Поинтер, способный указывать на очередной элемент множества и сдвигаться на следующий элемент того же множества, или быть принудительно связан с любым другим.

Отличается не так уж сильно. Я позволил себе выделить в цитате место, которое, на мой взгляд, к повторению и перебору не имеет никакого отношения.

К перебору - не имеет. Просто в си++ итератор не привязан к множеству пожизненно, можете его связать с другим (совместимым), больше ничего.
Чтобы закончить с "неизвестными специалистами", могу предложить общеизвестную "трактовку" итератора в си++ для ясности: "Итератор - это то, что может быть использовано, как итератор."

На самом деле, проблема итераторов C++ именно в их перегруженности функционалом.

Пример итератора из Си++:

Код: Выделить всё

int* iter;

что вы называете перегруженностью функционалом?
В результате, в C++ цель получить "итератор вообще" не достигнута, зато разведен бардак с кучей итераторов, обладающих разными возможностями.

Перечитайте выше "общеизвестное определение из си++". Я что-то не понимаю, о каком "еще более вообще" итераторе вы мечтаете?? А разных итераторов с стандартной библиотеке всего пять категорий. Да и из тех... истрим_итератор вообще-то дефектный... Так что где вы нашли кучу итераторов - тоже уточнить бы. Все остальные "итераторы" подпадают под одну из категорий, и многие из них никто в жизни не видит и в явной форме не создает.

Поясняю еще раз:
watashiwa_darede... писал(а):
21.11.2007 11:15
что-то вроде шелловского: command | grep pattern | sort | uniq.

но для объектов. Еще бы аналог tee не помешал. Если интересно, могу продемонстрировать решение этой задачки для, например, Python, но в отдельной ветке -- создайте, если вам действительно интересно.

Сорт-уник к итераторам отношения не имеют - ни к плюсовым, ни к вашим правильным. Это алгоритмы. Соответственно, остается что? комманд - это источник данных, т.е. бегин и енд, греп - фильрующий итератор. Но следом идет сорт, значит нам все равно нужно отдельное множество, оптимизированное для сортировки. Следом из этого множества мы удаляем дубликаты. Итак:

Код: Выделить всё

std::list<T> command;
std::vector<T> out;
// и три строки кода на все:

std::copy_if(command.begin(), command.end(), std::back_inserter(out), & grep);
std::sort(out.begin(), out.end());
std::unique_copy(out.begin(), out.end(), std::ostream_iterator<T>(std::cout, ","));

При многократном юзании оформляете в функцию.
И что, вы и вправду для такого случая стали бы собирать "просто и легко производный итератор"??? ну вы даете... (фигеет) :happy:
И еще мну не вполне понимает, как этот производный итератор будет сортировать? уник сделать как фильтрующий итер понятно, а вот сортировка не вполне...

Вот-вот. Проблема C++-итераторов как раз в том, что они -- "пойнтер". По хорошему, итератор -- это НЕ пойнтер.

Это не по-хорошему, это по-вашему. Что не тождественно. :happy: А в си++ итератор есть то, что ведет себя как итератор. Где вы видели более общее определение-то? Расскажите наконец. )))

Про "недеструктивно использовано" и "(N+1)!" не понял, если честно.

Есть там оговорка, что удалять элементы из множества надо с оглядкой... больше ничего. А про факториал я сглючил, там не факториал а ((N + 1) ^ 2) /2 или как-то так получается. Так вы кстати не ответили на вопрос, как я должен правильными итераторами на одном списке объектов пометить для себя дюжину другую нужным мне подмножеств???

За счет простоты создания производных итераторов достигается гораздо большая гибкость. Нафига мне какой-то мифический (N+1)! последовательностей?

Вам нафига, а мне нужны. С неправильными итераторами я их имею, а вы покажите как я их с правильными получу. Потому что если никак - то и итераторы ваши никакие не правильные, а кошкин хвост, вот.
Мне нужны вполне определенные: скажем, итератор обхода дерева в ширину, итератор обхода дерева в глубину (которых, как и деревьев, к слову, в std нет), и простые, но гибкие способы создания производных итераторов.

Хватит голословия. Вы пока одну задачу поставили - я ее решил элементарно и без всякой зауми и ненужной писанины с производными итераторами. Вы мою - вообще не смогли решить. Сперва дайте хоть какой-нибудь ответ - потом дальше пойдем.
А деревьев нет в стандарте, значит они есть в других библиотеках. Раз нет в стандарте - то о чем тогда тут говорить? Какие претензии к стандарту? И кто вам, скажите на милость, мешает в дереве иметь методы, возвращающие те и другие итераторы для обхода так и для обхода этак? Или создать несколько классов, способных обходить дерево так или этак, реализую контракт итератора? Не пробовали? - попробуйте. Мне кажется, должно получиться...
Debian GNU/Linux 4 -- AMD Athlon64 3000+ / Asus 7600GS -- Gnome
Debian GNU/Linux 5 -- Dell (Vostro) 500 (Celeron M560 / iGM965) -- Gnome
Спасибо сказали:
Аватара пользователя
serzh-z
Бывший модератор
Сообщения: 8259
Статус: Маньяк
ОС: Arch, Fedora, Ubuntu

Re: C vs. C++

Сообщение serzh-z »

Поскольку отделить в новый топик такую кучу постов не представляется возможным, тема просто была переименована в соответствии с уходом темы в спор про итераторы.
Спасибо сказали:
Аватара пользователя
drBatty
Сообщения: 8735
Статус: GPG ID: 4DFBD1D6 дом горит, козёл не видит...
ОС: Slackware-current

Re: C vs. C++

Сообщение drBatty »

watashiwa_daredeska писал(а):
20.11.2007 11:22
Спорить не буду. Может, подскажешь, пару вещей

что значит shared object? Если ты про подключение *.dll в MSVC - читай MSDN, гдето-там галку надо поставить... Здесь это оффтопик, имхо... А твой std::vector Страуструп так подробно разжевал, что даже дажёвывать нечего, есть и русский перевод в сети.
http://emulek.blogspot.ru/ Windows Must Die
Учебник по sed зеркало в github

Скоро придёт
Осень
Спасибо сказали:
Аватара пользователя
drBatty
Сообщения: 8735
Статус: GPG ID: 4DFBD1D6 дом горит, козёл не видит...
ОС: Slackware-current

Re: C vs. C++

Сообщение drBatty »

v04bvs писал(а):
21.11.2007 18:03
Мне итераторы не нравятся потому, что без автовывода типов строка "for (std::vector<int>::const_iterator i = a.begin(); i != a.end(); ++i)" выглядит абсолюто дико и не читаемо.

делай как я:

Код: Выделить всё

my_iterator j;
for(j = 0; j < 15; j++);

Этот цикл перебирает первые 15 объектов. естественно где-то в коде есть конструктор по умолчанию, перегруженный =(int), перегруженное преобразование в int(или оператор < ), ну и собственно ++. А std::vector я не использую, больно он обобщённый, и поэтому дорогой.
И вообще, беда стандартных шаблонов в том, что там очень много всего напихано ненужного. И нет мгогово нужного. Вот тут один господин решил писать софт для паровозов - он просто не имеет право использовать std::sort, обычно она сортирует быстро и хорошо, но иногда жутко тормозит. Ему что-нибудь более медленное, но на 100% надёжное надо. Придётся ковырять ему все сырцы своей std(а кто сказал, что у него будет gcc&ix86?). Не проще ли написать свой надёжный и переносимый код? Ведь сила С++ в том, что программист может создать свой тип, с нужной именно ему функциональностью. Если юзать только std::string, не проще ли писать на бейсики, где уже есть в стандарте такой тип и другого не будет?
http://emulek.blogspot.ru/ Windows Must Die
Учебник по sed зеркало в github

Скоро придёт
Осень
Спасибо сказали:
watashiwa_daredeska
Бывший модератор
Сообщения: 4038
Статус: Искусственный интеллект (pre-alpha)
ОС: Debian GNU/Linux

Re: C vs. C++

Сообщение watashiwa_daredeska »

drBatty писал(а):
22.11.2007 13:36
где-то в коде есть конструктор по умолчанию, перегруженный =(int), перегруженное преобразование в int(или оператор < )

Для итератора нельзя перегрузить эти операторы для (int), т.к. итератор в принципе не знает, к какому контейнеру он относится. В этом и проблема.

drBatty писал(а):
22.11.2007 13:36
А std::vector я не использую, больно он обобщённый, и поэтому дорогой.

std::vector настолько же дешевый, как и C-массив, выделенный в динамической памяти.
Спасибо сказали:
watashiwa_daredeska
Бывший модератор
Сообщения: 4038
Статус: Искусственный интеллект (pre-alpha)
ОС: Debian GNU/Linux

Re: C vs. C++

Сообщение watashiwa_daredeska »

drBatty писал(а):
22.11.2007 13:09
что значит shared object? Если ты про подключение *.dll в MSVC - читай MSDN, гдето-там галку надо поставить...

Ну, в Linux в частности, dll'ки называются shared object. И динамическая загрузка в runtime (например, плагин) -- это не "галку надо поставить", а сделать вызов функции. Проблема в том, что POSIX API ориентировано на C и противоречит стандарту C++, т.к. для использования функции из библиотеки нужно преобразовать void* в void(*)(), что запрещено стандартом C++. А своего API в "самостоятельном" C++ для этого нет.
Спасибо сказали:
watashiwa_daredeska
Бывший модератор
Сообщения: 4038
Статус: Искусственный интеллект (pre-alpha)
ОС: Debian GNU/Linux

Re: C vs. C++

Сообщение watashiwa_daredeska »

sergio писал(а):
21.11.2007 19:45
что вы называете перегруженностью функционалом?

То, что итераторы используются для всех операций с контейнерами. Поиск, извлечение, вставка, удаление, перестановка, все вообще делается через итераторы. Есть, конечно, shortcut-методы и операторы, которые позволяют обойтись без итератора в частных случаях, но они все реализованы тривиально через те же итераторы.

Иногда это приводит к совершенно диким конструкциям, вроде remove/erase.

sergio писал(а):
21.11.2007 19:45
Я что-то не понимаю, о каком "еще более вообще" итераторе вы мечтаете??

Я как раз не мечтаю об "итераторе вообще". Мне нужен очень простой итератор, который для тривиальных случаев реализуется в 3-5 строк полностью в соответствии с требуемым интерфейсом.

sergio писал(а):
21.11.2007 19:45
Сорт-уник к итераторам отношения не имеют - ни к плюсовым, ни к вашим правильным.

Как ни странно, имеют. Конечно, sort -- это итератор "с особенностями", который сначала получает всю последовательность, а потом выплевывает на выход, но тем не менее, по результату sort можно итерировать, а внутренности меня интересуют, но по другой причине.

sergio писал(а):
21.11.2007 19:45
std::copy_if(command.begin(), command.end(), std::back_inserter(out), & grep);

Т.е. command должен реализовать собственный итератор, чтобы его можно было в copy_if передать подобным образом? Кроме того, в shell, command выдает данные на stdout и приведенный пайплайн выдает данные на stdout, т.е. у них общий интерфейс. Я могу и то, и другое использовать как вход другого пайплайна, принимающего на входе и обрабатывающего строки того вида, который выдает command. Приведенный вами код меняет интерфейс. Это не то. Мне нужен унифицированный интерфейс, чтобы я мог строить программу из блоков, как в shell.

В случае повсеместного использования промежуточных векторов и OutputIterator, происходит совершенно лишний расход памяти (я не говорю про случай с sort).

Пример реализации на Python:

Код: Выделить всё

from itertools import ifilter

def isort( iterable ) :
  forSort = list( iterable )
  forSort.sort()
  return iter( forSort )

def iuniq( iterable ) :
  class First : pass
  prev = First
  for i in iterable :
    if prev != i :
      prev = i
      yield i

def grepSortUniq( predicate, iterable ) :
  return iuniq( isort( ifilter( predicate, iterable ) ) )


sergio писал(а):
21.11.2007 19:45
Где вы видели более общее определение-то?

Что в вашем понимании означает "более общее"?

sergio писал(а):
21.11.2007 19:45
А про факториал я сглючил, там не факториал а ((N + 1) ^ 2) /2 или как-то так получается.

А что вы, собственно, считали-то?

sergio писал(а):
21.11.2007 19:45
как я должен правильными итераторами на одном списке объектов пометить для себя дюжину другую нужным мне подмножеств???

Если считать произвольные упорядоченные подмножества, то их на самом деле, несколько больше, чем N(N+1)/2 и даже N!. Например, мне может потребоваться подпоследовательность "через один" или "два вперед один назад" и т.п. В случае с простыми итераторами, я создаю производный итератор с нужными мне свойствами и использую. При этом, в большинстве случаев, я могу этот нетривиальный алгоритм обхода легко построить на базе простого итератора, сделав его, таким образом, абсолютно независимым от контейнера или вообще его наличия.

Код: Выделить всё

# Пример обобщенного итератора "через один" на Python (без использования itertools):
def oddElements( iterable ) :
  for i, e in enumerate( iterable ) :
    if i % 2 :
      yield e

# Пример
oddList = list( oddElements( someList ) )

# Бесполезный сумасшедший пример, удаляющий половину+-1 элементов словаря
oddDict = dict( oddElements( someDict.iteritems() ) )

# Получение с i-го по j-й элемент последовательности oddElements при помощи itertools
oddSubList = list( itertools.islice( oddElements( someList ), i, j ) )

Заметьте, что на самом деле, oddElements сам использует итератор, полученный из функции enumerate и вся цепочка итераторов в последнем выражении относительно эффективна по памяти (насколько Python может быть эффективен :) ) -- не создается никаких промежуточных контейнеров в размере O(n).
Спасибо сказали:
d_n_k
Сообщения: 636
ОС: Gentoo GNU/Linux

Re: C vs. C++

Сообщение d_n_k »

watashiwa_daredeska, вы бы еще код на каком-нибудь функциональном языке привели и говорили что на с++ так сделать нельзя, поэтому он плохой
все сказанное есть имхо...
Спасибо сказали:
watashiwa_daredeska
Бывший модератор
Сообщения: 4038
Статус: Искусственный интеллект (pre-alpha)
ОС: Debian GNU/Linux

Re: C vs. C++

Сообщение watashiwa_daredeska »

d_n_k писал(а):
23.11.2007 14:01
watashiwa_daredeska, вы бы еще код на каком-нибудь функциональном языке привели и говорили что на с++ так сделать нельзя, поэтому он плохой

Вот и именно, что Python -- не функциональный, а вполне себе императивный, т.е. идеологически в той же нише, что и C++.
Спасибо сказали:
Аватара пользователя
drBatty
Сообщения: 8735
Статус: GPG ID: 4DFBD1D6 дом горит, козёл не видит...
ОС: Slackware-current

Re: C vs. C++

Сообщение drBatty »

watashiwa_daredeska писал(а):
23.11.2007 09:09
drBatty писал(а):
22.11.2007 13:36
где-то в коде есть конструктор по умолчанию,

Для итератора нельзя перегрузить эти операторы для (int), т.к. итератор в принципе не знает, к какому контейнеру он относится. В этом и проблема.
нет. для меня итератор - это то, что можно сдвинуть к сл. ++, или(возможно) перейти напрямую [] и уж точно, вернутся к началу. Возможно для твоего итератора я и не прав, для меня это не догма, всего лишь термин. Целые числа тут к месту, к примеру i = 0 трактуется, как перейти к первому.
drBatty писал(а):
22.11.2007 13:36
А std::vector я не использую, больно он обобщённый, и поэтому дорогой.

std::vector настолько же дешевый, как и C-массив, выделенный в динамической памяти.
Ага, ЩаЗ блин! Отсортируй-ка мне матрицу 2^21*2^21 символов своим vector'ом, и мы посмотрим, что дороже. Или почитай исходные тексты bzip'а(вдруг ты скажешь, что это не имеет смысла).
http://emulek.blogspot.ru/ Windows Must Die
Учебник по sed зеркало в github

Скоро придёт
Осень
Спасибо сказали:
d_n_k
Сообщения: 636
ОС: Gentoo GNU/Linux

Re: C vs. C++

Сообщение d_n_k »

Вот и именно, что Python -- не функциональный, а вполне себе императивный, т.е. идеологически в той же нише, что и C++.

не знаешь, не говори глупостей
http://www.google.com/search?ie=UTF-8&...nal+programming
все сказанное есть имхо...
Спасибо сказали:
watashiwa_daredeska
Бывший модератор
Сообщения: 4038
Статус: Искусственный интеллект (pre-alpha)
ОС: Debian GNU/Linux

Re: C vs. C++

Сообщение watashiwa_daredeska »

drBatty писал(а):
23.11.2007 23:37
нет. для меня итератор - это то, что можно сдвинуть к сл. ++, или(возможно) перейти напрямую [] и уж точно, вернутся к началу.

Для примера, возьмем функцию с сигнатурой:

Код: Выделить всё

template < typename T >
std::vector<T>::iterator doSomething( std::vector<T>::iterator i );

Функция получает произвольный итератор на произвольный элемент вектора. Приведи, пожалуйста, пример кода тела функции, который позволит получить итератор начала и конца вектора, на который указывает i. Я, видимо, чего-то не догоняю.

drBatty писал(а):
23.11.2007 23:37
Целые числа тут к месту, к примеру i = 0 трактуется, как перейти к первому.

Можно увидеть пример реализации такого оператора?

drBatty писал(а):
23.11.2007 23:37
Ага, ЩаЗ блин! Отсортируй-ка мне матрицу 2^21*2^21 символов своим vector'ом, и мы посмотрим, что дороже. Или почитай исходные тексты bzip'а(вдруг ты скажешь, что это не имеет смысла).

bzip2 написан на C, а не на C++. "Отсортировать матрицу" -- без проблем, если будет определение того, что это значит.

d_n_k писал(а):
25.11.2007 01:48
не знаешь, не говори глупостей
http://www.google.com/search?ie=UTF-8&...nal+programming

На таком уровне ФП есть и в C++, что не делает его функциональным языком. Ни в C++, ни в Python нет хотя бы элементарной оптимизации хвостовой рекурсии, что делает проблематичным написание хоть сколько-нибудь значимых участков кода в ФП-стиле.

drBatty писал(а):
23.11.2007 23:37
Отсортируй-ка мне матрицу 2^21*2^21 символов своим vector'ом

Кстати, не заглядывая в исходники bzip2, зуб даю, что матрицу размером 2^21*2^21 = 2^42 bzip2 не сортирует хотя бы потому, что на большинстве современных компьютеров она не влезет в ОЗУ.
Спасибо сказали:
Аватара пользователя
drBatty
Сообщения: 8735
Статус: GPG ID: 4DFBD1D6 дом горит, козёл не видит...
ОС: Slackware-current

Re: C vs. C++

Сообщение drBatty »

watashiwa_daredeska писал(а):
28.11.2007 08:13
Для примера, возьмем функцию с сигнатурой:

Код: Выделить всё

template < typename T >
std::vector<T>::iterator doSomething( std::vector<T>::iterator i );

Функция получает произвольный итератор на произвольный элемент вектора. Приведи, пожалуйста, пример кода тела функции, который позволит получить итератор начала и конца вектора, на который указывает i. Я, видимо, чего-то не догоняю.

Теперь вы можете описывать вектора типа vector почти столь же
элегантно, как и вектора, встроенные в сам язык:

vector v1(100); vector v2(nelem*2-4);

Операцию доступа можно определить как

int& vector::operator[](int i) {
if(i<0 || sz<=i) error("vector index out of range");
// индекс выходит за границы вектора
return v[i];
}

ну и далее по тексту... Или я текст не авторитетный взял?(про итераторы там дальше есть).
drBatty писал(а):
23.11.2007 23:37
Отсортируй-ка мне матрицу 2^21*2^21 символов своим vector'ом

Кстати, не заглядывая в исходники bzip2, зуб даю, что матрицу размером 2^21*2^21 = 2^42 bzip2 не сортирует хотя бы потому, что на большинстве современных компьютеров она не влезет в ОЗУ.
И не жалко тебе твоего зуба? А как Кнут свои матрицы 1000*1000 считает, на своём MIX'е, где памяти - пара килобайт? А вот у создателей bzip'а - влезает такая матрица. Кстати, в топик: а почему бзип написан на Си? Почему не на Си++ с использованием std::vector? Наверное не потому, что авторы не знали таких вещей, просто они им не подошли. И пришлось им изобретать свои итераторы и свои велосипеды, ибо чужие, так любимые тобой std::, требывали компьютер с 2^42 памяти(как ты правильно заметил), а ещё процессора с быстродействием 2^42Hz. А ты говоришь - не дороже. Дороже, если нужна особая организация памяти и/или особые алгоритмы работы. Про агоритмы: сортировка в std делит множество на 2 части, а вот сортировка в bzip - на три. Конечно, можно написать костыль, однако с таким подходом от твоего vector'а останутся одни костыли... А сам bzip можно и на C++ написать, только с другими классами(оборачивать их в шаблон, как vector, не имеет смысла).

PS: Про алгоритмы используемые в bzip можно почитать хотя бы здесь. Ну и google, естественно...
http://emulek.blogspot.ru/ Windows Must Die
Учебник по sed зеркало в github

Скоро придёт
Осень
Спасибо сказали:
watashiwa_daredeska
Бывший модератор
Сообщения: 4038
Статус: Искусственный интеллект (pre-alpha)
ОС: Debian GNU/Linux

Re: C vs. C++

Сообщение watashiwa_daredeska »

drBatty писал(а):
28.11.2007 11:02
ну и далее по тексту... Или я текст не авторитетный взял?

М-м-м... У вас с логикой все в порядке? Я не знаю, что это за текст, во-первых. Во-вторых, это не ответ на поставленный вопрос: как имея только один итератор на произвольный элемент вектора получить итератор на начало и итератор на конец вектора. В-третьих, индексы -- это даже близко не итераторы.


drBatty писал(а):
28.11.2007 11:02
А как Кнут свои матрицы 1000*1000 считает, на своём MIX'е, где памяти - пара килобайт? А вот у создателей bzip'а - влезает такая матрица.

Где это он там считает такие матрицы в общем виде? Желательно том, номер раздела. По-быстрому нашел только т.1, раздел 2.2.6 -- там рассматривается матрица всего 200x200 и то, разреженная.
Спасибо сказали:
watashiwa_daredeska
Бывший модератор
Сообщения: 4038
Статус: Искусственный интеллект (pre-alpha)
ОС: Debian GNU/Linux

Re: C vs. C++

Сообщение watashiwa_daredeska »

drBatty писал(а):
28.11.2007 11:02
Кстати, в топик: а почему бзип написан на Си? Почему не на Си++ с использованием std::vector? Наверное не потому, что авторы не знали таких вещей, просто они им не подошли. И пришлось им изобретать свои итераторы и свои велосипеды, ибо чужие, так любимые тобой std::, требывали компьютер с 2^42 памяти(как ты правильно заметил), а ещё процессора с быстродействием 2^42Hz. А ты говоришь - не дороже. Дороже, если нужна особая организация памяти и/или особые алгоритмы работы.

Открою страшную тайну, если бы авторам bzip2 не нравился только std::vector, они бы могли использовать C-массивы в C++. Видимо, им не понравился сам C++. И на это есть особые причины, никак не связанные с кривостью итераторов std или накладными расходами std::vector. А если у массива есть неявная внутренняя структура, то это уже не просто массив. Например, трехдиагональную матрицу можно хранить в std::vector с не меньшей эффективностью, чем в C-массиве. Никто ведь не запрещает тебе организовать, например, heap в std::vector (для heapsort).

Кроме того, предлагаю подумать над выводом следующей программы (скомпилированной в release-варианте, естественно):

Код: Выделить всё

#include <iostream>
#include <vector>
int main()
{
    std::cout << sizeof(int*) << '\n' << sizeof( std::vector<int>::iterator ) << '\n';
    return 0;
}
Спасибо сказали:
Аватара пользователя
drBatty
Сообщения: 8735
Статус: GPG ID: 4DFBD1D6 дом горит, козёл не видит...
ОС: Slackware-current

Re: C vs. C++

Сообщение drBatty »

watashiwa_darede... писал(а):
28.11.2007 12:00
Во-вторых, это не ответ на поставленный вопрос: как имея только один итератор на произвольный элемент вектора получить итератор на начало и итератор на конец вектора.
Для этого нужен такой итератор, который знает,на какой вектор он указывает. К примеру, можно хранить указатель на вектор в итераторе. Вот тогда можно будет получить от вектора указатель на любой элемент. А цитата из Страуструпа(какой-то древний перевод, книжки под рукой нет)...

watashiwa_darede... писал(а):
28.11.2007 12:00
Где это он там считает такие матрицы в общем виде?
Вот в том то и дело! Вот и в bzip'е возникают матрицы не в "общем виде". Да и вообще, только в учебных задах и в std::vector есть векторы общего вида. А в реальной жизни вид вполне конкретен, но шаблон вектора всё равно тянет за собой не нужную конкретно сейчас функциональность. И не добавляет необходимой в данном конкретном случае.
http://emulek.blogspot.ru/ Windows Must Die
Учебник по sed зеркало в github

Скоро придёт
Осень
Спасибо сказали:
watashiwa_daredeska
Бывший модератор
Сообщения: 4038
Статус: Искусственный интеллект (pre-alpha)
ОС: Debian GNU/Linux

Re: C vs. C++

Сообщение watashiwa_daredeska »

drBatty писал(а):
28.11.2007 11:02
Про агоритмы: сортировка в std делит множество на 2 части, а вот сортировка в bzip - на три. Конечно, можно написать костыль, однако с таким подходом от твоего vector'а останутся одни костыли...

Да хоть на 4. Какая разница? Написать можно и не костыль, а нормальную шаблонную функцию, которая будет сортировать вектора с любым типом элементов. От вектора останется ровно столько же, сколько и от C-массива.

Значит так, drBatty, я прекращаю с вами дискуссию на эту тему. Причины, по которым bzip2 написан на C и не использует std::vector не имеют ничего общего с тем, о чем вы думаете.
Спасибо сказали:
watashiwa_daredeska
Бывший модератор
Сообщения: 4038
Статус: Искусственный интеллект (pre-alpha)
ОС: Debian GNU/Linux

Re: C vs. C++

Сообщение watashiwa_daredeska »

drBatty писал(а):
28.11.2007 12:26
Для этого нужен такой итератор, который знает,на какой вектор он указывает. К примеру, можно хранить указатель на вектор в итераторе.

Вы, видимо, не следите за ходом дискуссии. Такого итератора в std нет. То, что его можно написать, я не сомневаюсь ни секунды, но его надо писать, причем вместе с полной заменой всех контейнеров std, для сохранения хотя бы той минимальной концептуальной целостности, которая в ней присутствует.

drBatty писал(а):
28.11.2007 12:26
А в реальной жизни вид вполне конкретен, но шаблон вектора всё равно тянет за собой не нужную конкретно сейчас функциональность. И не добавляет необходимой в данном конкретном случае.

Интересно услышать, какую-такую функциональность (да еще столь тяжеловесную) тянет за собой шаблон вектора, и какую-такую функциональность предоставляет C-массив и не предоставляет std::vector?

P.S. Ах, да, я же обещал прекратить эту дискуссию :)
Спасибо сказали:
Аватара пользователя
drBatty
Сообщения: 8735
Статус: GPG ID: 4DFBD1D6 дом горит, козёл не видит...
ОС: Slackware-current

Re: C vs. C++

Сообщение drBatty »

watashiwa_darede... писал(а):
28.11.2007 12:45
Ах, да, я же обещал прекратить эту дискуссию :)
Не будем ссориться по таким пустякам. Вам удобнее std::vector - удачи. Я же не настаиваю. ;)

PS: Кстати я не считаю обычный массив в стиле Си хорошей мыслью. Мне думалось мы ведём спор про std::vector vs не_std::vector.
http://emulek.blogspot.ru/ Windows Must Die
Учебник по sed зеркало в github

Скоро придёт
Осень
Спасибо сказали: