лямбда-исчисление

Компьютеры, программы, периферия, коммуникации, интернет, программирование и т.п. Ранее назывался Hard-n-Soft.
Сообщение
Автор
radhar

№ 0 Сообщение radhar » 01 окт 2009 15:43

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

Понятное, дело что речь идет не о функциональных языках =)

Ну, я в С++ восновном в foreach его применяю. Реально облегчает жизнь.
А где вы?

Pedro
Аватара пользователя
Поблагодарили: 623 раза

№ 1 Сообщение Pedro » 01 окт 2009 15:57

Это как-то связано с кончиной выдающегося грузинского писателя Отар Чиладзе?

radhar

№ 2 Сообщение radhar » 01 окт 2009 16:01

Не, просто решил провести интересующий меня опрос.
А на отара мне насрать. Так же как на стрэйзи и кинорежисёра.

djdance
Аватара пользователя
Благодарил (а): 1 раз
Поблагодарили: 4 раза

№ 3 Сообщение djdance » 05 окт 2009 23:12

0: radhar:
>лямбда-исчисление.

я пока не догнал, как его можно практически применить. Тем более в форыче. Покажи кусок.

demien

№ 4 Сообщение demien » 06 окт 2009 01:11

3: djdance:
растусуй для малограмотных, что за тема такая лямбда-исчесление. может оно мне позарез надо, жизнь спасёт, а я и не знаю ничего про эту вещь.
на википедии я читать не стал, там жутко математически всё. ничё непонятно

djdance
Аватара пользователя
Благодарил (а): 1 раз
Поблагодарили: 4 раза

№ 5 Сообщение djdance » 06 окт 2009 01:15

4: demien:
забей, работа на уровне букв

demien

№ 6 Сообщение demien » 06 окт 2009 10:05

5: djdance:
ну вот :(
поеду тогда на работу, быдлокодерством заниматься без лямбда програмирования.

radhar

№ 7 Сообщение radhar » 06 окт 2009 11:53

Ну, вот примерчик
for_each(a.begin(), a.end(),
if_then(_1 % 2 == 0, cout << _1));

Это с документации бустовой.

По мне очень удобно.
Особенно если использовать с бустовым bind

souphead
Аватара пользователя
Благодарил (а): 3 раза
Поблагодарили: 10 раз

№ 8 Сообщение souphead » 07 окт 2009 11:07

Ну типа вот так пользуйся напремер:

лямбда+лямбда=двалямбда
двалямбда+лямбда=трилямбда
двалямбда+трилямбда=пятьлямбда
и тэдэ

radhar

№ 9 Сообщение radhar » 07 окт 2009 11:17

souphead пишет:
> Ну типа вот так пользуйся напремер:
>
> лямбда+лямбда=двалямбда
> двалямбда+лямбда=трилямбда
> двалямбда+трилямбда=пятьлямбда
> и тэдэ

Немного не понял о чём ты?
От лямбды большая польза в алгоритмах.
Простейший пример, когда ты вызываешь алгоритм sort - ему первыми двумя параметрами передаются итераторы на начало и конец контейнера. А третим - компаратор.
Если использовать стандартную библиотеку, то тебе придётся отдельно писать свой компаратор, а это затрудняет чтение кода.

А с помощью Lambda ты спокойно можешь написать что-то типа std::sort(cont.begin(), cont.end(), _1 < _2);
И сразу всё ясно.
Ну, для такого простого случая компаратор и стандартный подойдёт. Но, если у тебя в контейнере лежат указатели.
std::sort(cont.begin(), cont.end(), *_1 < *_2);
Что намного понятнее и удобнее, чем писать свой компаратор.

djdance
Аватара пользователя
Благодарил (а): 1 раз
Поблагодарили: 4 раза

№ 10 Сообщение djdance » 07 окт 2009 11:19

9: radhar:
а как в общем случае работает компаратор, ему все равно, что подсовывать? нет ли неопределенности?

radhar

№ 11 Сообщение radhar » 07 окт 2009 11:26

В смысле?
компаратор (compare) сравнивает два элемента.
Определяет на множестве отношение <.
В случае lambda получается лучшая абстракция. Т.к. нет зависимости от типа.
В случае с STL компаратором - это всего лишь бинарный предикат. И у него большая зависимость от типа.

djdance
Аватара пользователя
Благодарил (а): 1 раз
Поблагодарили: 4 раза

№ 12 Сообщение djdance » 07 окт 2009 11:30

11: radhar:
ну так я и говорю, насколько он всеяден?
или как в php - наплевать на типы?

ну ты уже ответил - зависимость есть. То есть надо держать в голове, какая функция-параметр что может ему скормить?

radhar

№ 13 Сообщение radhar » 07 окт 2009 11:36

lamda - всеяден.
то есть для (_1 + _2) будет пофиг какие типы. Главное чтобы у них была операция +.
(ну, собственно связывание происходит на этапе компиляции. То есть о полной всеядности говорить не могу).

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

Всё таки это С++, а не хаскель.
Так что полной всеядности тут нема =)

djdance
Аватара пользователя
Благодарил (а): 1 раз
Поблагодарили: 4 раза

№ 14 Сообщение djdance » 07 окт 2009 11:47

13: radhar:
а как выглядит механизм этой вот аддитивности (+)? на примере. Интересует именно синтаксическая реализация. Не параметром же?

radhar

№ 15 Сообщение radhar » 07 окт 2009 11:51

class A
{
private:
int i_;
public:
A(int i = 0) : i_(i) {}
A& operator += (const A & a)
{
i_ += a.i_;
return *this;
}
A operator +(const A& a) const
{
A b(*this);
b += a;
return b;
}
}

int main()
{
A a(3), b(5);
A c;
c = a + b;
a += b;
return 0;
}

Вот простейший пример =)

djdance
Аватара пользователя
Благодарил (а): 1 раз
Поблагодарили: 4 раза

№ 16 Сообщение djdance » 07 окт 2009 11:57

15: radhar:
аа, то есть явно в классе задаем что и как будет меняться. Условно говоря, помучавшись один раз, потом не будем подсовывать циклу переменные быдлокодом. Ну прикольно. Но надо привыкать. Интересно, а если цикл циклится, как искать ошибку? :D

radhar

№ 17 Сообщение radhar » 07 окт 2009 12:02

Ну, если у классы можно сравнивать - то у них должна быть определена операция < (ну и желатьльно > <= и т.п.).
Просто как ты будешь сравнивать, если у тебя в контейнере лежат не сами экземпляры класса, а указатели на них?

std::list<std::string *> l;

Можно сделать или так:
bool compare (std::string* a, std::string* b) { return *a < *b };
std::sort(l.begin(), l.end(), compare);


Либо сделать с помощью lambda
std::sort(l.begin(), l.end(), *_1 < *_2);

Согласись, что второй вариант намного лучше =) И понятнее.

radhar

№ 18 Сообщение radhar » 07 окт 2009 12:06

А по поводу - цикл циклится. То искать как обычно. Дебагером.
Или ты про какой цикл?

Кстати, вместо циклов лучше использовать алгоритмы.
например тот же for_each. Это просто обёртка над for, для избежания ошибок и более ясного представления кода.

list<string*>::iterator it;
for_each(l.begin(), l.end(), it)
{
cout << *(*it) << endl;
}

Хотя мне больше нравится использовать бустовый
BOOST_FOREACH(string * s, l)
cout << *s << endl;

djdance
Аватара пользователя
Благодарил (а): 1 раз
Поблагодарили: 4 раза

№ 19 Сообщение djdance » 07 окт 2009 12:07

17: radhar:
понятнее, но кажный раз надо все определять - на заморока?
а готовых наборов наверное нет смысла держать

radhar

№ 20 Сообщение radhar » 07 окт 2009 12:10

Я немного не понял, про что ты. Что определять?
Готовых наборов куча. Это и контейнеры, и алгоритмы и ещё куча всякой вкусности =)
Помимо самого C++ и его STL. Ещё активно используются библиотеки ACE ( для кроссплатформенного и распределённого программирования) и boost(это расширение STL по сути. Там куча алгоритмов, те же lambda и много всего.)

djdance
Аватара пользователя
Благодарил (а): 1 раз
Поблагодарили: 4 раза

№ 21 Сообщение djdance » 07 окт 2009 12:15

20: radhar:
>Я немного не понял, про что ты. Что определять?
ну что ж ты хочешь, я ж пытаюсь выражаться на уровне "нахватался по верхам" ;)
но ответ ясен - уже наваляли пакетов. Хорошо вам, кто врубился! :rtfm:

djdance
Аватара пользователя
Благодарил (а): 1 раз
Поблагодарили: 4 раза

№ 22 Сообщение djdance » 07 окт 2009 12:16

я вот только теперь заинтересовался, что такое здесь этот буст.

radhar

№ 23 Сообщение radhar » 07 окт 2009 12:17

Ну, да. Когда изучешь библиотеки - намного быстрее и красивее прогать получается.
И гораздо лучше.
Правда изучается С++ с основными библиотеками очень долго.
Классики пишут, что лет 10 надо, чтобы стать профессионалом.
Я с ними полностью согласен.
Счас как раз углубляю свои знания в boost и ACE

Вернуться в «Компьютерный форум»

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и 0 гостей