- 01
- 02
- 03
- 04
- 05
- 06
- 07
- 08
- 09
- 10
- 11
public class CollectionUtils {
public static function removeFromArray(_target_array:*, _element_for_deleting:*):void {
try {
var index:int = _target_array.lastIndexOf(_element_for_deleting);
if (index >= 0)
_target_array.splice(index, 1);
} catch (e:Error) {
RGB.entry.debug.throwError('CollectionUtils.removeElement() use only for Array or Vector');
}
}
}
kyzi007 19.12.2012 11:02 # 0
TarasB 19.12.2012 11:19 # 0
http://www.joelonsoftware.com/items/2003/10/13.html
roman-kashitsyn 19.12.2012 12:12 # +3
TarasB 19.12.2012 12:48 # 0
bormand 19.12.2012 13:12 # +2
Функции низкого уровня типа readByte, readFloat кидают экцепшн если файл кончился или не читается, или же возвращают прочитанное значение. Если мы видем некорректные данные - тоже кидаем экцепшн. Вокруг всего этого стоит один трай-кетч, который ловит экцепшн, и превращает его в код возврата.
Вот здесь без экцепшена код превратится в сраное говнище, где чтение каждого поля обрамлено в if. А никаких бед в данном случае экцепшены не принесут, да и даже не провалятся за пределы функции загрузки, и не будут мешать тем, кто их не любит...
slavara 19.12.2012 13:24 # 0
TarasB 19.12.2012 13:28 # 0
Steve_Brown 19.12.2012 13:54 # +1
А когда логика программы перемешана с кучей проверок на ошибки (и не забыть проверить все случаи!), то это уже, может, и математически строже, но ни фига не понятней.
Ну и потом, иногда лучше подстраховаться, чем перестраховаться. Ошибка вероятна (неверный пользовательский ввод) - надо все проверить. Ошибка маловероятна (некорректные внутренние данные) - тратить время и место на проверку всего и вся не стоит. Тут достаточно сказать "извините, что-то не так, пошлите трейс разработчику". Или если ошибка в коде - тут все равно сделать ничего нельзя.
Если не ядро пишем и не программу для АЭС.
TarasB 19.12.2012 14:42 # −2
Я вот беру, и читаю:
{ do1; do2; do3; }
и я точно знаю, что если вы вошли в этот блок, то стопудов вызовется do3. Конечно, и на исключениях можно обрести уверенность, надо всего-навсего сделать так:
TarasB 19.12.2012 14:42 # −3
3.14159265 19.12.2012 16:19 # +2
Меня тоже подбешивает писать try-catch для таких мест, но и без исключений еще хуже (в тех местах где они нужны).
TarasB 19.12.2012 21:14 # −3
LispGovno 19.12.2012 22:10 # +1
TarasB 20.12.2012 09:32 # −3
Я точно не могу так взять, и сходу привести пример. Но случаи, когда я вижу код и понимаю, что если он выйдет в середине (в точке без явного выхода), то будет полная лажа - случатся достаточно часто. Если бы это было не так, то тогда бы не изобрели такую хитрую жопу, как транзакции, как раз на случай недовыполненности действия.
LispGovno 20.12.2012 10:40 # +1
Тебе в хаскель. Там я слышал есть STM, хотя в лицо никогда его не видел.
LispGovno 20.12.2012 10:47 # +1
TarasB 20.12.2012 10:53 # +1
Хорошо, тогда скажи, как правильно написать процедуру FreeAndNil?
Так?
или так?
Так вот, в траеблядстве таких траеблядских вопросов, в каком же блядь порядке выполнять какие-то там операции, дохуя, и траеблядские грабли подстерегают тебя на каждом шагу только потому что ты какую-то хрень сделал после другой хрени, а раии на всех не оберёшься, а вот стоит только постулировать, что такой-то код никогда не выкинет исключение, а если и выкинет, то только из-за грубой ошибки программиста, то сразу же всё упрощается в несколько раз.
Моя экспоненциально растущая лесенка, кстати, абсолютно корректна, если вы не поняли.
LispGovno 20.12.2012 12:05 # 0
TarasB 20.12.2012 12:06 # +1
bormand 20.12.2012 17:26 # +3
TarasB 21.12.2012 20:54 # 0
Кодовозвратобоги презирают ваши проблемы!
3.14159265 21.12.2012 20:59 # +3
Сходи-ка на сосач. Тамошняя публика с радостью и пониманием воспримет твои ультразеленые идеи о ненужности эксепшонов.
TarasB 21.12.2012 21:04 # 0
3.14159265 21.12.2012 21:30 # 0
Можно писать 90% без единого try~catch~finally. А исключения и обрабатывать ловить в самом верху.
bormand 21.12.2012 21:31 # +1
3.14159265 21.12.2012 21:34 # +2
Вот именно. Он никогда не писал их и говорит.
С одного счета клиента деньги сняли, но на другой не перевели из-за клинча, foreign key error, переполнения итд. А код Тараса пошел дальше, сделал всё что надо и в конце закомитился, в итоге клиент остался без денег и в страшном гневе бежит разбираться - как же так. Хе-хе.
Ну или писать ifы на каждый чих.
Может в геймдеве и полезно игнорить исключения - чтобы игра не падала по пустякам.
3.14159265 21.12.2012 21:30 # +3
fixed
TarasB 21.12.2012 21:37 # −2
3.14159265 21.12.2012 21:41 # +3
Я тебе еще раз объясняю, если ты работаешь с данными, то надо проверять каждый чих любой insert, update или вызов процедуры может не сработать.
А не будешь проверять - похерится целостность.
Так и try~catch не надо злоупотреблять. Многие просто не понимают где их надо ставить. И из-за паранойи лепят в каждой функции.
TarasB 21.12.2012 21:44 # −1
Мне такие вещи попадаются редко. А вообще у микрософта есть простой метод для таких вещей, в ядре используется.
> Так и try~catch не надо злоупотреблять. Многие просто не понимают где их надо ставить. И из-за паранойи лепят в каждой функции.
Более, того они ещё и кидают throw на каждый чих, в итоге вместо портянки ифов имеем портянку катчей, ну и нахрена это ради чего?
bormand 21.12.2012 21:48 # +3
Ключевое слово мне.
LispGovno 22.12.2012 02:49 # 0
Что-за метод?
bormand 21.12.2012 21:47 # +3
Ага, а теперь взгляни на любую никсовую или виндовую апишку... Или кодовозвратобоги не опускаются до написания операционных систем, и, как хаскелисты, пишут исключительно абстрактный код в вакууме, который никак не взаимодействует с реальностью?
TarasB 21.12.2012 21:52 # +1
3.14159265 21.12.2012 21:54 # +3
Ладно бы ты говорил о мире юникса. Я бы понял. Но тут ключевое слово _все_.
Но как раз та ОС, которую ты чаще всего юзаешь, и написана на исключениях.
Там ведь не сигналы, а именно SEH. MS даже свою сишку этим расширяла. Так что слив, гы-гы-гы.
bormand 21.12.2012 22:04 # +2
И сколько же процентов кода в ядре игнорирует коды возврата других функций, и выглядит как do1; do2; do3? А сколько там функций, не возвращающих код ошибки?
P.S. У исключений по сравнению с кодом возврата есть большой плюс - на них сложно забить. Если ты не проверил код возврата, и что-то вдруг пошло не так - ты в полной жопе. Как ты будешь дебажить проблему, которая из-за этого вылезает у одного юзера из ста раз в месяц при невыясненных обстоятельствах, я не знаю. Читать гигабайты логов? Если же вылетело исключение, то в той же богомерзкой жабе у тебя будет стектрейс, который поможет тебе в разборе полётов.
LispGovno 22.12.2012 02:47 # +1
bormand 20.12.2012 17:46 # +1
Да я верю, что она корректна для определенной задачи. Но ведь эта задача и на ифах и кодах возврата будет смотреться не лучше ;) Если думаешь что лучше - приведи пример, как бы ты решил поставленную тобой выше задачу на кодах возврата. (Я так понимаю, что переход от линейной структуры из твоего коммента чуть выше к этой лестнице произошел из-за того, что нужна разная постобработка в зависимости от результатов операций?)
TarasB 21.12.2012 19:04 # 0
do1;do2;do3;
это если код изначально заточен на работу без исключений.
Steve_Brown 21.12.2012 19:13 # 0
bormand 21.12.2012 20:21 # +1
Нихрена подобного. Код Тараса забивает на возможные ошибки и продолжает исполнение. Не буду обсуждать плохо это или хорошо, видимо задача так требует. А данный код с траем может упасть на do1 и не выполнить do2 и do3. Полный аналог:
TarasB 21.12.2012 20:47 # 0
Код с самого начала пишется так, чтобы ничто никогда не кидало исключения. И библиотеки компилируются с соответствующими флагами.
Лол, траебляди настолько тупые, что ваще не вдупляют, как какая-то сторонняя функция может не кидать исключения)))
bormand 21.12.2012 21:21 # +3
И игнорирует возвращаемое значение, говорящее об ошибке (если оно конечно есть)... Иначе бы тут стояли ифы, не правда ли?
А почему они игнорируются? Либо, в плохом случае, разраб ленивый пидорас, и ему похуй на то что прога будет молча творить хуйню, и при этом даже не падать. Либо, в хорошем случае, разраб умён и настолько уверен в том, что при исполнении этих функций не может произойти никаких проблем, что он объявил их как void, и не возвращает никаких кодов ошибок. Но в этом случае тот самый умный программист и в крестах может пометить функции do1() .. do3() как не бросающие исключений, и спокойно их вызывать.
> Лол, траебляди настолько тупые, что ваще не вдупляют, как какая-то сторонняя функция может не кидать исключения)))
throw() в описании крестофункции же.
TarasB 21.12.2012 21:29 # −1
Но ведь траеблядская проблема в том, что они и нормалньые функции переписывают в траеблядский стиль! И даже признак того, что мы дошли до конца массива у некотрых является исключением, и когда каждая вторая функция становится траеблядской, код становится писать намного сложнее.
bormand 21.12.2012 21:38 # +3
В математической задаче полностью согласен. А в задачах, приближенных к реальному миру, как правило почти в каждой функции могут возникнуть проблемы - диск закончился, памяти нет, сектор сбойнул и байт прочитался не так, закрылся сокет, юзер умер за клавиатурой... И если на эти ошибки ложить хуй (они ведь очень редкие!), то программа вроде бы работает, но иногда молча сделает что-то не так... в лучшем случае недосчитает зарплату ее разрабу... А молчаливые ошибки - это самые страшные ошибки, никакой краш от пропущенного исключения не сравнится с ними.
roman-kashitsyn 22.12.2012 08:24 # +4
Тарас просто давно не писал сишного системного кода, где каждый вызов может закончится фейлом. А надо последовательно занять пяток ресурсов, а если что-то не удалось, освободить в обратном порядке, а могут придти сигналы...
bormand 22.12.2012 09:10 # +2
Ну вот, кстати, в OpenGL (с которым как-раз, наверное, работает Тарас) большинство функций написаны так, что они не могут возвращать ошибок. Почему? А потому что, емнип, любая команда OpenGL, которая захочет получить от драйвера какой-то ответ (glGet*, glGetError), будет ждать до тех пор, пока не выполнятся все команды, стоящие перед ней, а это убивает производительность вхлам. Поэтому об ошибке (вернее об ее почти бесполезном коде, без указания даже APIшки, которая ее вызвала) можно узнать только пост-фактум, в основном уже после конца кадра и свопа буферов...
Можно, конечно, для локализации бага сделать сборку игры, в которой после каждой команды будет стоять glGetError...
Видимо поэтому геймдевовцы, в том числе и Тарас, привычны к большим кускам кода, которые игнорят ошибки.
LispGovno 22.12.2012 10:41 # 0
И как это влияет на код?
roman-kashitsyn 22.12.2012 11:06 # +3
bormand 22.12.2012 11:51 # 0
Если программы на том конце сокетов\пайпов написаны корректно, и адекватно реагируют на обрыв - все будет хорошо. Проблемы разве что с расшаренной памятью.
roman-kashitsyn 22.12.2012 11:52 # 0
LispGovno 22.12.2012 11:59 # 0
bormand 22.12.2012 12:11 # 0
Несколько тредов захватили семафор, один из них подох. Что делать дальше - непонятно. Поэтому система поступает самым тупым и очевидным образом - не меняет при этом счетчик семафора, все равно ресурс, который был им защищен, уже распидорасило.
bormand 22.12.2012 12:06 # +3
Причем виндовые вроде бы тоже. Для мутексов там запилили результат WAIT_ABANDONED, который возвращается треду, который ждал мутекса, а захвативший мутекс поток сдох без освобождения. Для семафоров же такого нет (или я не находил).
Плата за скорость семафоров + shm...
LispGovno 22.12.2012 12:12 # 0
bormand 22.12.2012 12:21 # +2
Можно, тут трабла не в реализации, а в том, что система должна сделать, если подох тред, держащий семофор. С мутексом все просто - уведомить его нового владельца о том, что ресурс распидорасило, и он попытается что-то восстановить. С семафором так не прокатит. У семафора нет определеного владельца. И один поток уже не сможет овладеть распидорашенным общим ресурсом и пофиксить его.
P.S. Поэтому не стоит убивать через kill -9 проги юзающие расшаренную память и семафоры... Остальные то сигналы они нормально обработают и все отпустят.
LispGovno 22.12.2012 22:01 # 0
А в чем проблема. Таймаут спасет отца русской демократии (этакий вотчдог).
bormand 22.12.2012 12:33 # +1
О как, покопался в мане по никсовым семафорам, нашел там флажок SEM_UNDO, который отменяет операцию над семафором при краше. Вот только логику, восстанавливающую ресурс, который защищал этот семафор, придется продумать самому.
TarasB 22.12.2012 12:49 # 0
roman-kashitsyn 23.12.2012 00:21 # +3
"Довольно-таки плохо" (с)
Ядро сигналов не боятся, оно же их пересылает. А вот организовать надёжную работу и взаимодействие нескольких прецессов порой бывает сродни чёрной магии.
Сама сигнатура функции signal как бы намекает, что неопытным товарищам с ней лучше не связываться (ого что я нашёл http://govnokod.ru/1319)
LispGovno 23.12.2012 00:48 # 0
TarasB 23.12.2012 01:31 # +1
bormand 23.12.2012 12:38 # 0
И правильно делаешь. Пока программа справляется со своей работой путем мультиплексирования ввода-вывода или запуском независимых параллельных процессов - ну ее нахуй эту многопоточность..
LispGovno 22.12.2012 02:40 # +1
Даже NotEnoughMemoryException?
bormand 22.12.2012 07:38 # +2
Ты что, Тарасоаллокатор возвращает null, и он каждый раз проверяет результат на него. Какие еще исключения?
roman-kashitsyn 20.12.2012 10:50 # +3
3.14159265 20.12.2012 17:32 # +2
Пишешь на методе @Transactional или @TransactionManagement и немедленно наступает щастье без try-catch.
PS А еще есть АОП, которым можно абсолютно любую оборачивающую логику (а не только транзакции, автоrollbackи или игнор эксепшенов ) на все методы по регэксу, написав злополучный try всего лишь раз.
Но Тарас просто находится в ужасном плену ndk-крестоблядства и ничего этого не знает.
LispGovno 20.12.2012 17:55 # 0
3.14159265 20.12.2012 17:58 # +2
Сюда входит и тот случай когда каждый вызов оборачивается try-catch.
LispGovno 20.12.2012 18:38 # 0
3.14159265 21.12.2012 20:17 # +2
Вот зря ты это упомянул транзакции. Ты судя по всем не работал и потому не знаешь.
Вот возьмем близкий пример диалект sqlя без исключений, и как сторонник вендоплатформы и юзер студии, то думаю хотя бы чуть-чуть работал MS SQL.
В прошлых версиях там не было исключений. А часто бизнес-логика написана на хранимках.
Вот пример c исключениями, когда любая ошибка в любой из вложеных хранимок приводит к откату транзакции, то код выглядит так:
А вот что нам предлагает Тарас, чтобы обеспечить целостность данных при переводе
LispGovno 22.12.2012 02:42 # 0
TarasB 22.12.2012 22:12 # +2
У меня вот процедура парсинга данных, введённых в форму вызывает парсинг каждой таблица, каждая таблица вызывает процедуру парсинга строк, те вызывают парсинг ячейки, короче вложение такое.
Ну и и меня код тупо такой:
if not ParseTable(Table1) then exit(false);
А, один лишь вопрос - куда записать информацию о том, где именно ошибка? Ну это не проблема, например, можно в возвращаемое значение.
У меня было брутально и бессердечно - программа не узнавала про то, где именно ошибка. Просто на самом нижнем уровне, если распарсить не удалось, то показывалось окно пользователю, типа чё за херь ты ввёл.
LispGovno 22.12.2012 22:48 # +1
А как же паттерн отделения бизнес логики от интерфейса взаимодействия с пользователем?
TarasB 22.12.2012 23:50 # 0
bormand 23.12.2012 12:40 # +2
TarasB 23.12.2012 12:53 # +1
bormand 23.12.2012 13:05 # 0
Можно конечно, но тут ты смешаешь в одной структуре две сущности - собственно распарсенные данные и ошибку их обработки, тем самым намертво связав структуру и ее парсинг. А это не всегда айс (например если есть несколько разных источников, из которых получают данную структуру, и у каждого есть своя инфа об ошибках).
P.S. Но это все равно на порядки лучше, чем статический getLastError.
TarasB 23.12.2012 13:19 # 0
А передавать подробную информацию об ошибке вместе с исключением - это крестоблядская ересь, в нормальных языках кроме кода исключения хуй ты что передашь. А, ну в Аде какого-то хуя ещё есть костыль - вместе с кодом можно кинуть строку.
LispGovno 23.12.2012 13:45 # +1
LispGovno 23.12.2012 13:42 # 0
Ты это Хаскелю скажи:
Either Error' Float, так что Тарас модный посан и пользуется хаскельными методиками.
bormand 23.12.2012 14:57 # +1
Это Тарас уже ниже написал Если не нравится, то передавай структуру {parserResult&, parserError&} смешивание будет только на верхнем уровне.. И это годный способ, т.к. ошибку можно будет отстегнуть.
А в том комменте он предлагал смешать поля с данными поля с ошибкой в одной структуре: Проще в ту структуру, в которую парсер пишет инфу, добавить поле для идентификации ошибки.
TarasB 23.12.2012 15:11 # +1
TParserData, TParserDataWithError : TParserData итд?
LispGovno 23.12.2012 15:15 # +1
LispGovno 24.12.2012 08:52 # 0
Steve_Brown 24.12.2012 10:08 # +2
LispGovno 24.12.2012 10:24 # 0
TarasB 24.12.2012 11:02 # +2
LispGovno 24.12.2012 12:12 # 0
roman-kashitsyn 24.12.2012 12:19 # +2
В boost полно нормальных либ. Мне вот unit_test очень понравилась.
LispGovno 24.12.2012 12:43 # 0
roman-kashitsyn 24.12.2012 13:29 # +2
LispGovno 24.12.2012 15:04 # 0
Неужели то что успел понюхать лучше жабовского фреймворка?
bormand 24.12.2012 15:15 # +1
Я правильно понимаю, что это толстый троллинг?
Мне жаба нравится как простой и понятный язык, но вот стандартная либа у нее, имхо, говно. И даже многие жабопрофессионалы тут со мной будут согласны.
roman-kashitsyn 24.12.2012 15:25 # +2
3.14159265 24.12.2012 15:37 # +3
Doug Lea. Особенно приложил руку ко второму.
На фоне остальной либы смотрится божественно.
Блох изначально разрабывал collections - тоже ниче, но местами говно кучукуется.
Кстати это в том числе строковой тред.
Добавлю String, StringBuiler(Buffer), CharSequence, Appendable - реально продуманные и удобные классы.
LispGovno 24.12.2012 15:54 # 0
bormand 24.12.2012 16:00 # 0
Буст большой. Тут скорее надо говорить про конкретные его куски, т.к. они всяко поддерживаются разными людьми.
LispGovno 24.12.2012 17:07 # 0
defecate-plusplus 24.12.2012 19:37 # +2
да ладно
перепроверь в релизе -O2
шаблонная версия?
у нас crc16 бустом считается в релизе быстрее, чем раньше 15 лет считался табличным методом (с длинной таблицей, причем)
bormand 24.12.2012 20:12 # +1
roman-kashitsyn 24.12.2012 21:59 # +1
roman-kashitsyn 19.12.2012 14:58 # +4
1. Написать макрос IGNORE_ERRORS( do1(); ) (С/С++)
2. Оформить do1/2/3 в виде комманд и использовать выполнятор комманд, ингорящий исключения (твой ООП язык здесь)
3. Написать функцию высшего порядка и использовать лямбды (твой функциональный язык тут)
4. Написать макрос, "отключающий" исключения как фичу языка (Lisp)
TarasB 19.12.2012 15:01 # 0
roman-kashitsyn 19.12.2012 15:16 # +3
Для этого есть одна отличная фича, называется "деструкторы". К сожалению, не везде есть, вместо неё в жабосишарпах есть try/using, в Python - context manager, в Go - defer.
wvxvw 19.12.2012 15:41 # 0
Сказать, чтобы от этого было легче, или, что проще понять что произошло врезультате ошибки, или что так легче программу написать - ой я бы сильно засомневался.
3.14159265 19.12.2012 16:08 # +3
LispGovno 19.12.2012 22:06 # +2
>except
>catch
>except
Ты где эту х*ню выкопал? Закапывай.
roman-kashitsyn 19.12.2012 14:18 # +4
В реальной жизни ничего против исключений не имею, считаю Спольски упоротым троллем.
3.14159265 19.12.2012 16:18 # +1
В ядре луникса есть еще одна причина - производительность.
>хотя ООП фишечки в ядре используются
Что именно? Передача указателя на функции? Таблицы этих самых функций?
Так это общепринятный подход. Его можно называть и функциональным и обзывать разными умными паттернами.
roman-kashitsyn 19.12.2012 16:26 # 0
3.14159265 19.12.2012 16:29 # +1
roman-kashitsyn 19.12.2012 16:32 # +4
bormand 19.12.2012 18:02 # +1
LispGovno 19.12.2012 22:14 # 0
bormand 20.12.2012 05:54 # 0
Лолчто? Ну разве что у них вся память пронумерована вверх-ногами.
Если первый "класс" имеет vtable, и все остальные расширяют этот "класс", тупо дописывая свои поля в конец, то смещение не нужно.
Собственно в с++ смещение при кастах возникает как раз в двух случаях - множественное наследование, и когда у предка нет виртуалок, а у потомка они есть.
roman-kashitsyn 20.12.2012 10:26 # +2
LispGovno 19.12.2012 22:04 # +2
Используй божественное RAII!
TarasB 20.12.2012 09:35 # 0
LispGovno 20.12.2012 12:21 # 0
Можешь ещё глянуть на маленький Loki::ScopeGuard.h, но он правда не лямбда-подобный, в отличии от удобного фрагмента выше, работающего на любом крестокомпиляторе, где работает буст.
Ну и пользуйтесь умными указателями, COM-указателями и прочими враперами, пригодными для работы.
kyzi007 19.12.2012 19:04 # +1
Трай кетч работает медленно это два.
И вообще мне этот метод с * не нравится.
wvxvw 19.12.2012 20:26 # 0
Удаление из массива можно сделать в один заход, вместо двух, но не известно, будет ли быстее, зато некоторые нативные типы, тот же ByteArray тоже можно будет использовать с этой функцией.
Т.е.:
Таким образом избегаем повторного просматривания элементов до найденого, не полагаемся на indexOf(), которого нет у ByteArray. Ну и не создаем лишних сущностей с ошибками.
wvxvw 19.12.2012 20:32 # 0
wvxvw 19.12.2012 20:39 # 0
kyzi007 19.12.2012 21:04 # 0
TarasB 19.12.2012 21:16 # 0
Эхх, я ведь статью для школьников писал, как это надо делать: http://forum.pascalnet.ru/index.php?showtopic=26642
wvxvw 19.12.2012 21:19 # 0
wvxvw 19.12.2012 21:23 # 0
TarasB 19.12.2012 21:30 # +2
Ёбаный в рот.
Прочитай мою статью для школоты ещё раз.
wvxvw 19.12.2012 21:40 # 0
3.14159265 19.12.2012 21:42 # 0
Понятно что статья для нубов.
А что если сделать структуру, суть которой - обертка для строк, которая содержит список ссылок на куски массивов с чарами (cow).
Ну то есть нам надо сделать replace('TarasBtarasBtaraS','B',' ').
Мы сохраняем ссылку на кусок исходной строки потом ссылку на пробел, итд.
В итоге новая строка будет содержать список массивов:
['Taras', ' ','taras',' ','taraS']
Профит - нет копирования памяти, быстрые инсерты.
Наша "виртуальная" строка может модифицироваться много раз, а когда будем выводить то обычно это выходной поток.
То есть копирование в принципе не надо.
LispGovno 19.12.2012 21:57 # +1
bormand 20.12.2012 06:17 # +3
roman-kashitsyn 20.12.2012 09:13 # +3
LispGovno 20.12.2012 10:44 # +1
roman-kashitsyn 20.12.2012 13:05 # +2
LispGovno 20.12.2012 15:15 # 0
Можно пример? Как-то пока не очень понятно как с этой структурой работать. Думаю на хаскеле это пару строк.
LispGovno 20.12.2012 15:16 # 0
3.14159265 20.12.2012 15:38 # +2
wvxvw 20.12.2012 18:09 # +1
(1 ((2 3) 4) (((((5))))) 6)
распечатается как 123456. Ну и соответственно, добавить в конец такого дерева дешевле, чем если бы оно было обычным списком.
хотим добавить 7 в конец:
(list (1 ((2 3) 4) (((((5))))) 6) 7) -> ((1 ((2 3) 4) (((((5))))) 6) 7)
LispGovno 20.12.2012 23:01 # 0
Картинка Roman.jpg:
3.14159265 20.12.2012 15:42 # 0
А в других языках есть что-то похожее?
И вообще есть ли научное название для деревообразного связного списка, элементы которого - другие списки (которые в свою очередь либо примитивны - массивы [частный случай - 1 элемент] ), либо такие же композитные списки.
roman-kashitsyn 20.12.2012 15:45 # +1
С виду похоже на Ropes
3.14159265 20.12.2012 16:00 # +1
Мне в голову ничего лучше Zipperа не приходило.
LispGovno 20.12.2012 16:52 # 0
3.14159265 20.12.2012 16:56 # 0
А я грю об эффективных строках и списках.
LispGovno 20.12.2012 23:05 # 0
3.14159265 20.12.2012 16:09 # 0
Но в реальных приложениях строки обычно никто не насилует. Если только это не текстовый редактор.
Зато в среднем все операции (поиск по индексу, вставка, замена) совершаются за логарифмическое время или быстрее.
А конкатенация так и вообще - константно, не зависит от длины строки
3.14159265 20.12.2012 16:20 # 0
LispGovno 20.12.2012 22:39 # 0
>ссылку на пробел
То есть это 5 байт в место одного? Конечно же нет. В 64хбитной системе это 9 байт вместо одного?
Но я конечно признаюсь: Будет ещё и длина строки. То есть как минимум 10 байт в 64х системе на один символ. А когда операций пройдет много и строка превратится в гигабайты 10тибайтовых символов. Ну и все эти dereference очень дорогая операция, тк не кешфрендли.
3.14159265 20.12.2012 23:03 # +1
Да.
>В 64хбитной системе это 9 байт вместо одного?
Да.
> Будет ещё и длина строки.
Обязательно. Хотя для чара можно сделать и отдельный класс.
Да. Со всем согласен.
>То есть как минимум 10 байт в 64х системе на один символ.
Нет.
Есть одна проблема - ты идиот.
Сохраняем ссылку на иммутабельный объект - строка.
Она создается 1 раз. 8 байт в 64-битной системе, 4 - в 32-х битной.
>А когда операций пройдет много и строка превратится в гигабайты 10тибайтовых символов
Выше я написал - мы всегда можем балансировать дерево.
Рекомендую для начала посчитать сколько будет стоит сделать много (пусть даже парочку) операций, на гигабайтовых строках обычным способом - через копирование массива.
wvxvw 19.12.2012 21:53 # 0
LispGovno 19.12.2012 22:01 # 0
В C# функция подобная этой вертает int, чтобы не генерировать исключения, тк функция низкоуровневая и боялись просадки производительности. (Уж и не знаю почему). Если ошибка, то она возвращает код, выходящий за диапазон байта.
bormand 20.12.2012 06:19 # +4
LispGovno 20.12.2012 07:08 # 0
http://govnokod.ru/12321
LispGovno 19.12.2012 22:02 # 0
Используй обертку Maybe.
3.14159265 21.12.2012 21:04 # +2
Я откажусь от своих слов, если мне предоставят доказательства того что Microsoft Excel написан без единого блока try~catch.
TarasB 21.12.2012 21:09 # 0
А он что, в одиночку писал ексель? Его не сдерживали контракты про то, что "эта функция может кинуть исключение, нельзя просто так продолжать писать код после неё"? А не после ли работы над екселем он сказал "да заебали!" и написал свою заметку?
guest 26.02.2013 02:25 # −1
LispGovno 19.12.2012 22:17 # 0