Объясните динозавру
От: Аноним  
Дата: 11.04.14 07:02
Оценка:
Почему это хорошо

BOOST_FOREACH(auto& file_name, files)
{
    if(boost::algorithm::ends_with(file_name, L"dll"))
    {
        ...
    }
}


а это

for (auto i = files.begin(); i != files.end(); i++)
{
    if (i->compare(i->size() - 3, 3, L"dll") == 0)
    {
        ...
    }
}


"ржу не могу всем отделом LOL" ???
Re: Объясните динозавру
От: Evgeny.Panasyuk Россия  
Дата: 11.04.14 07:19
Оценка: 1 (1) +1
Здравствуйте, Аноним, Вы писали:

А>Почему это хорошо


Разве не очевидно?

А>
А>BOOST_FOREACH(auto& file_name, files)
А>for (auto i = files.begin(); i != files.end(); i++)
А>


Первый вариант намного проще + читающий сразу понимает, что в теле foreach будет просмотрено каждое значение, без скачков.
Второй вариант — более error-prone, плюс в теле возможны скачки типа i-=10.

А>
А>if(boost::algorithm::ends_with(file_name, L"dll"))
А>if (i->compare(i->size() - 3, 3, L"dll") == 0)
А>


В первом варианте нет ничего лишнего — два значения и вызов предиката — проще и быть не может (разве что специальный кроссплатформенный предикат is_dynamic_library_name, но это уже другая логика).
Во втором же варианте добавляются вычисления с жёстко прибитыми длинами, опять же более error prone.

А>"ржу не могу всем отделом LOL" ???


А это скорее показатель культуры отдела.
Re: Объясните динозавру
От: Trrrrr  
Дата: 11.04.14 07:19
Оценка: 1 (1) +2
Ну в общем особо то не важно, но если четко брать 2ой вариант, то проблема магические числа:

а если разрешение будете искать не dll а html, а тот кто залезет в код забудет тройки поменять?
Что будет если i->size() — 3 это выражение меньше нуля?

В первом коде таких проблем нет.
Re: Объясните динозавру
От: Son of Northern Darkness  
Дата: 11.04.14 07:23
Оценка: 5 (2) +3
Здравствуйте, Аноним, Вы писали:

А>
А>for (auto i = files.begin(); i != files.end(); i++)
А>{
А>    if (i->compare(i->size() - 3, 3, L"dll") == 0)
А>    {
А>        ...
А>    }
А>}
А>


А>"ржу не могу всем отделом LOL" ???


Второй вариант оформления цикла мне нравится больше (что может понравиться в нестандартном макросе?).
А вот во втором варианте в условии, скорее всего, ошибка. Если имя файла короче трех символов мы будем иметь неопределенное поведение.
Re: Объясните динозавру
От: oziro Нигерия  
Дата: 11.04.14 07:28
Оценка:
Вот это вот: "i", "size()", "3 и Lлитерал" — не тривиально и глаз зацепляется. У некоторых еще за "i++" будет зацепляться.

"i" заменить на file_name_it
size на length (они эквиваленты)

3 и Lлитерал на const std::wstring ext = L"dll"; ... // ext.length() вместо 3

Тогда будет не так топорно. Буст не обязателен.
Re: Объясните динозавру
От: rusted Беларусь  
Дата: 11.04.14 07:33
Оценка: 1 (1) +2
Здравствуйте, Аноним, Вы писали:

Первый вариант легко починить, заменив условие на
boost::algorithm::iends_with(file_name, L".dll")


Во втором варианте аналогичные исправления сделают и так громоздкий код еще более неуклюжим.
Re: Объясните динозавру
От: Alexander G Украина  
Дата: 11.04.14 07:58
Оценка: +1
К уже сказанному выше.

Цикл первого варианта уже можно заменить на стандартную конструкцию
for (auto& file_name : files)

> for (auto i = files.begin(); i != files.end(); i++)

end() вычисляется каждый раз, на практике эта операция не может быть закеширована в регистр или стек.
в случае первого варианта end() вычисляется оидн раз.
Русский военный корабль идёт ко дну!
Re: Объясните динозавру
От: saf_e  
Дата: 11.04.14 08:02
Оценка:
Здравствуйте, Аноним, Вы писали:

А>Почему это хорошо


А>
А>BOOST_FOREACH(auto& file_name, files)
А>{
А>    if(boost::algorithm::ends_with(file_name, L"dll"))
А>    {
А>        ...
А>    }
А>}
А>


А>а это


А>
А>for (auto i = files.begin(); i != files.end(); i++)
А>{
А>    if (i->compare(i->size() - 3, 3, L"dll") == 0)
А>    {
А>        ...
А>    }
А>}
А>


А>"ржу не могу всем отделом LOL" ???


Раз есть auto, значит должна быть и лямбда, чем плох такой вариант?:

std::for_each(files.begin(), files.end(), [](const file &)
{
...
});
Re[2]: Объясните динозавру
От: Son of Northern Darkness  
Дата: 11.04.14 08:06
Оценка: +1
Здравствуйте, saf_e, Вы писали:

_>
_>std::for_each(files.begin(), files.end(), [](const file &)
_>{
_>...
_>});
_>


Обычно такое не удобно отлаживать. В каждой итерации приходится проваливаться в код std, да и читаемость ниже.
Re[2]: Объясните динозавру
От: Evgeny.Panasyuk Россия  
Дата: 11.04.14 08:19
Оценка:
Здравствуйте, saf_e, Вы писали:

А>>"ржу не могу всем отделом LOL" ???

_>Раз есть auto, значит должна быть и лямбда, чем плох такой вариант?:

_>
_>std::for_each(files.begin(), files.end(), [](const file &)
_>{
_>...
_>});
_>


Только отсутствием полиморфной лямбды (если же выписывать decltype — то довольно неуклюже будет выглядеть). (+лучше тогда уже boost::for_each)
Re: Объясните динозавру
От: B0FEE664  
Дата: 11.04.14 08:22
Оценка:
Здравствуйте, Аноним, Вы писали:

А>Почему это хорошо

А>
А>BOOST_FOREACH(auto& file_name, files)
А>

Это плохо использованием макроса

А>а это

А>
А>for (auto i = files.begin(); i != files.end(); i++)
А>

можно соптимизировать

А>
А>    if (i->compare(i->size() - 3, 3, L"dll") == 0)
А>

UB, как уже было указано.

А>"ржу не могу всем отделом LOL" ???

Действительно. Оба примера содержат ошибку. Попробуйте такие имена как "ItIsNotdll", "dll".
И каждый день — без права на ошибку...
Re[3]: Объясните динозавру
От: Evgeny.Panasyuk Россия  
Дата: 11.04.14 08:22
Оценка:
Здравствуйте, Son of Northern Darkness, Вы писали:

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


Про отладку ещё можно понять, но с читаемостью-то что?
Наоборот, ведь, выше — сразу видно что код выполнится для каждого элемента.
Re[4]: Объясните динозавру
От: Son of Northern Darkness  
Дата: 11.04.14 08:26
Оценка:
Здравствуйте, Evgeny.Panasyuk, Вы писали:

EP>Про отладку ещё можно понять, но с читаемостью-то что?

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

Да подсветка, например.
Re[5]: Объясните динозавру
От: Evgeny.Panasyuk Россия  
Дата: 11.04.14 08:28
Оценка:
Здравствуйте, Son of Northern Darkness, Вы писали:

EP>>Про отладку ещё можно понять, но с читаемостью-то что?

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

А что с подсветкой?
Re[6]: Объясните динозавру
От: Son of Northern Darkness  
Дата: 11.04.14 08:32
Оценка:
Здравствуйте, Evgeny.Panasyuk, Вы писали:

EP>Здравствуйте, Son of Northern Darkness, Вы писали:


EP>>>Про отладку ещё можно понять, но с читаемостью-то что?

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

EP>А что с подсветкой?


for (;) — это стандартная синтаксическая конструкция, где ключевое слово будет подсвечено соответствующим образом.
Но у меня на чтение того же куска ушло бы на несколько секунд дольше. Впрочем, мы можем сойтись на мнении, что я тупой и не понимаю лямбд.
Re[2]: Объясните динозавру
От: niXman Ниоткуда https://github.com/niXman
Дата: 11.04.14 08:44
Оценка: 1 (1)
Здравствуйте, Alexander G, Вы писали:

AG>end() вычисляется каждый раз, на практике эта операция не может быть закеширована в регистр или стек.

AG>в случае первого варианта end() вычисляется оидн раз.
не совсем так.
компилятор смотрит, если по отношению к 'files' применяются только константные методы, то 'files.end()' вычисляется только один раз. (говорю про GCC)
пачка бумаги А4 стОит 2000 р, в ней 500 листов. получается, лист обычной бумаги стОит дороже имперского рубля =)
Re[3]: Объясните динозавру
От: Evgeny.Panasyuk Россия  
Дата: 11.04.14 08:47
Оценка:
Здравствуйте, niXman, Вы писали:

AG>>end() вычисляется каждый раз, на практике эта операция не может быть закеширована в регистр или стек.

AG>>в случае первого варианта end() вычисляется оидн раз.
X>не совсем так.
X>компилятор смотрит, если по отношению к 'files' применяются только константные методы, то 'files.end()' вычисляется только один раз. (говорю про GCC)

Не может такого быть, из-за mutable или хотя бы указателей. Компилятору нужно доказать что результат не меняется.
Re[4]: Объясните динозавру
От: saf_e  
Дата: 11.04.14 08:50
Оценка:
Здравствуйте, Evgeny.Panasyuk, Вы писали:

EP>Здравствуйте, niXman, Вы писали:


AG>>>end() вычисляется каждый раз, на практике эта операция не может быть закеширована в регистр или стек.

AG>>>в случае первого варианта end() вычисляется оидн раз.
X>>не совсем так.
X>>компилятор смотрит, если по отношению к 'files' применяются только константные методы, то 'files.end()' вычисляется только один раз. (говорю про GCC)

EP>Не может такого быть, из-за mutable или хотя бы указателей. Компилятору нужно доказать что результат не меняется.


Вполне может иметь место хак применительно к стандартным контейнерам у нас есть гарантия, что вызывая только конст методы контейнер останется иммьютебл.
Re[5]: Объясните динозавру
От: Evgeny.Panasyuk Россия  
Дата: 11.04.14 08:54
Оценка:
Здравствуйте, saf_e, Вы писали:

EP>>Не может такого быть, из-за mutable или хотя бы указателей. Компилятору нужно доказать что результат не меняется.

_>Вполне может иметь место хак применительно к стандартным контейнерам

Это требует кооперации между GCC и библиотекой, скорей всего каких-то атрибутов. А вот есть ли такие атрибуты?

_>у нас есть гарантия, что вызывая только конст методы контейнер останется иммьютебл.


AFAIK, не immutable, а thread-safe, что более слабая гарантия.
Re[4]: Объясните динозавру
От: niXman Ниоткуда https://github.com/niXman
Дата: 11.04.14 08:57
Оценка:
Здравствуйте, Evgeny.Panasyuk, Вы писали:

EP>Не может такого быть, из-за mutable или хотя бы указателей. Компилятору нужно доказать что результат не меняется.

просто проверь.
пачка бумаги А4 стОит 2000 р, в ней 500 листов. получается, лист обычной бумаги стОит дороже имперского рубля =)
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.