Python: map vs for
От: Аноним  
Дата: 05.03.09 12:48
Оценка:
Интересует вопрос: насколько применение map дает выигрыш по скорости по сравнению с обычным for? Т.е. в теории оно, наверное, должно давать, а на практике — есть у кого-нибудь опыт применения, может кто-то видел в литературе оценки? Заранее спасибо.
Re: Python: map vs for
От: Daevaorn Россия  
Дата: 05.03.09 12:54
Оценка:
Здравствуйте, Аноним, Вы писали:

А>Интересует вопрос: насколько применение map дает выигрыш по скорости по сравнению с обычным for? Т.е. в теории оно, наверное, должно давать, а на практике — есть у кого-нибудь опыт применения, может кто-то видел в литературе оценки? Заранее спасибо.


Тут надо сравнивать не с обычным for, который конечно же медленее, а с list comprehension (LC). Тогда если у вас есть какой-то внешний функтор, то они практически равносильны. А вот если у вас lambda, то лучше LC, потому что он не будет тратить время на её вызов при каждой итерации.

Но в любом случае, если вы озаботились этим вопросом, то возможно, вы выбрали совсем не тот инструмент.
Re[2]: Python: map vs for
От: DemAS http://demas.me
Дата: 05.03.09 14:12
Оценка: +1
> Но в любом случае, если вы озаботились этим вопросом, то возможно, вы
> выбрали совсем не тот инструмент.

Согласен.
Это "синтаксический сахар" основная цель которого, повысить читабельность
программы, а на производительность он влияет крайне слабо.
Posted via RSDN NNTP Server 2.1 beta
Re[3]: Python: map vs for
От: Аноним  
Дата: 05.03.09 14:23
Оценка:
Здравствуйте, DemAS, Вы писали:


>> Но в любом случае, если вы озаботились этим вопросом, то возможно, вы

>> выбрали совсем не тот инструмент.

DAS>Согласен.

Охохо, и когда же на РСДНе перестанут на вопрос "как сделать то-то и то-то" отвечать вопросом "А нафиг тебе это надо?"....

DAS>Это "синтаксический сахар" основная цель которого, повысить читабельность

DAS>программы, а на производительность он влияет крайне слабо.
"-Где факты? — возмущенно закричал капитан.
-Да вот, вчера...... у боцмана в......, чувствую — ..... попахивает.....
"
(из обсцентного морского юмора)
Это я к тому, что мне тоже так показалось по результатам собственного эксперимента, но — может что-то не так делаю, и на самом деле скорость при использовании map и reduce должна возрастать?
Re[4]: Python: map vs for
От: DemAS http://demas.me
Дата: 05.03.09 14:52
Оценка:
"Аноним 336" <0@users.rsdn.ru> writes:

> DAS>Согласен.

> Охохо, и когда же на РСДНе перестанут на вопрос "как сделать то-то и то-то" отвечать вопросом "А нафиг тебе это надо?"....

1) А где вопрос "как сделать то-то и то-то"?
2) А где ответ "А нафиг тебе это надо?"?

Вопрос был — "правда ли что выигрыша в скорости нет".
Ответ был — "да, выигрыша в скорости нет".

Вопроса, "как получить выигрыш в скорости" я не увидел.


> "-Где факты? — возмущенно закричал капитан.

[...]
> Это я к тому, что мне тоже так показалось по результатам собственного
> эксперимента, но — может что-то не так делаю,

Для меня правильно поставленный эксперимент является одним из фактов на
основании которого я делаю для себя вывод.
Posted via RSDN NNTP Server 2.1 beta
Re[5]: Python: map vs for
От: Аноним  
Дата: 05.03.09 15:09
Оценка:
Здравствуйте, DemAS, Вы писали:

DAS>Вопроса, "как получить выигрыш в скорости" я не увидел.


Цитата:
Интересует вопрос: насколько применение map дает выигрыш по скорости по сравнению с обычным for? Т.е. в теории оно, наверное, должно давать, а на практике — есть у кого-нибудь опыт применения, может кто-то видел в литературе оценки? Заранее спасибо.

Так вот, ни опыта применения, ни ссылок на литературу я в ответ не получил. Только, прости, общие слова про "синтаксический сахар".

DAS>Для меня правильно поставленный эксперимент является одним из фактов на

DAS>основании которого я делаю для себя вывод.

Если б я был на 100% (ну, не буду жадничать, на 99,99%) уверен, что я все правильно делаю — я бы и не стал писать в форум. Меня интересует ,повторяю еще раз, личный опыт автора либо ссылки на авторитетный источник (Гвидо Ван подойдет вполне).
Re[6]: Python: map vs for
От: haba_haba_haba Россия  
Дата: 05.03.09 15:35
Оценка:
Здравствуйте, Аноним, Вы писали:

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


А>Если б я был на 100% (ну, не буду жадничать, на 99,99%) уверен, что я все правильно делаю — я бы и не стал писать в форум. Меня интересует ,повторяю еще раз, личный опыт автора либо ссылки на авторитетный источник (Гвидо Ван подойдет вполне).


Гвидо рассуждает на тему map, reduce и lambda:
http://www.artima.com/weblogs/viewpost.jsp?thread=98196

Старое обсуждение map vs list comprehension:
http://groups.google.com/group/comp.lang.python/browse_thread/thread/ec3529dbbc0881ba/43d59c57c1a2b126

Я бы использовал list comprehension для чего-нить короткого, однострочного и for для всего остального.
Re[6]: Python: map vs for
От: DemAS http://demas.me
Дата: 05.03.09 18:13
Оценка:
"Аноним 336" <0@users.rsdn.ru> writes:

> Цитата:

> Интересует вопрос: насколько применение map дает выигрыш по скорости по сравнению с обычным for? Т.е. в теории оно, наверное, должно давать, а на практике — есть у кого-нибудь опыт применения, может кто-то видел в литературе оценки? Заранее спасибо.

Ну а чем мой первоначальный ответ не вписался в этот вопрос?
Опыт имел. Увеличения скорости не заметил. Более того, не ожидал его даже
увидеть, ибо данная синтаксическая конструкция создавалась не для
увеличения производительности.

> Так вот, ни опыта применения, ни ссылок на литературу я в ответ не получил. Только, прости, общие слова про "синтаксический сахар".


Ну, ссылок у меня не осталось. Но общими словами идею, славу богу, выразить
я пока могу
Posted via RSDN NNTP Server 2.1 beta
Re: Python: map vs for
От: Nuald Россия http://nuald.blogspot.com
Дата: 06.03.09 01:29
Оценка: 1 (1)
Здравствуйте, Аноним, Вы писали:

А>Интересует вопрос: насколько применение map дает выигрыш по скорости по сравнению с обычным for? Т.е. в теории оно, наверное, должно давать, а на практике — есть у кого-нибудь опыт применения, может кто-то видел в литературе оценки? Заранее спасибо.


Вот, я набросал маленький пример:

""" Module for testing map performance. """
from math import sin, pi, exp

FUN = lambda x: exp(sin(pi/1.0 * x))
RANGE = xrange(1000)


def test_map():
    """ Test map function. """
    return map(FUN, RANGE)


def test_comprehension():
    """ Test list comprehension. """
    return [FUN(item) for item in RANGE]


def test_for():
    """ Test usual for statement. """
    result = []
    for item in RANGE:
        result.append(FUN(item))
    return result


TESTS = ('test_map', 'test_comprehension', 'test_for')


def main():
    """ The entry point. """
    from timeit import Timer
    timer = lambda test: Timer('%s()' % test, 'from __main__ import %s' % test)
    output = lambda test: '%s: %f' % (test, timer(test).timeit(number = 1000))
    print '\n'.join(output(test) for test in TESTS)

if __name__ == '__main__':
    main()


Запустил три раза (сам timeit прогоняет функции по 1000 раз, но можно поставить любое другое число), получил следующее:
[nuald@avalon ~]$ python test.py
test_map: 2.047035
test_comprehension: 2.076748
test_for: 2.466674
[nuald@avalon ~]$ python test.py
test_map: 2.290568
test_comprehension: 2.258289
test_for: 2.567286
[nuald@avalon ~]$ python test.py
test_map: 2.053508
test_comprehension: 2.099922
test_for: 2.414784

Т.е. скорость map и list comprehension сопоставима, for — медленнее. Но for делает append для списка (чтобы полностью продублировать функциональность), что и сказывается на тормозах. А вообще все рекомендуют юзать именно list comprehension, а pylint даже ругается на использование map.
Re[2]: Python: map vs for
От: Аноним  
Дата: 06.03.09 07:47
Оценка:
Здравствуйте, Nuald, Вы писали:
.....

Я позволил себе несколько нарушить Ваш копирайт (надеюсь, Ваш код распространяется на правах GPL? ) и на основе Вашего кода написал следующее:


""" Module for testing map performance. """
from math import sin, pi, exp

FUN = lambda x: exp(sin(pi/1.0 * x))
N = 100000
RANGE = xrange(N)


def test_map():
    """ Test map function. """
    return map(FUN, RANGE)


def test_comprehension():
    """ Test list comprehension. """
    return [FUN(item) for item in RANGE]


def test_for():
    """ Test usual for statement. """
    result = []
    for item in RANGE:
        result.append(FUN(item))
    return result

def test_for_smart():
    """ Test optimized for statement. """
    result = [None] * N
    for item in RANGE:
        result[item] = FUN(item)
    return result

TESTS = (test_map, test_comprehension, test_for, test_for_smart)


def main():
    """ The entry point. """
    from profile import Profile
    for case in TESTS:
        profiler = Profile()
        profiler.runcall(case)
        profiler.print_stats()

if __name__ == '__main__':
    main()


И вот чего получил:


300004 function calls in 0.581 CPU seconds

Ordered by: standard name

ncalls tottime percall cumtime percall filename:lineno(function)
100000 0.101 0.000 0.101 0.000 :0(exp)
1 0.109 0.109 0.580 0.580 :0(map)
1 0.001 0.001 0.001 0.001 :0(setprofile)
100000 0.105 0.000 0.105 0.000 :0(sin)
100000 0.264 0.000 0.471 0.000 iterations.py:4(<lambda>)
1 0.000 0.000 0.580 0.580 iterations.py:9(test_map)
1 0.000 0.000 0.581 0.581 profile:0(<function test_map at 0x00A9D430>)
0 0.000 0.000 profile:0(profiler)


300003 function calls in 0.585 CPU seconds

Ordered by: standard name

ncalls tottime percall cumtime percall filename:lineno(function)
100000 0.101 0.000 0.101 0.000 :0(exp)
1 0.001 0.001 0.001 0.001 :0(setprofile)
100000 0.103 0.000 0.103 0.000 :0(sin)
1 0.112 0.112 0.584 0.584 iterations.py:14(test_comprehension)
100000 0.267 0.000 0.471 0.000 iterations.py:4(<lambda>)
1 0.000 0.000 0.585 0.585 profile:0(<function test_comprehension at 0x00A9D470>)
0 0.000 0.000 profile:0(profiler)


400003 function calls in 0.767 CPU seconds

Ordered by: standard name

ncalls tottime percall cumtime percall filename:lineno(function)
100000 0.086 0.000 0.086 0.000 :0(append)
100000 0.101 0.000 0.101 0.000 :0(exp)
1 0.001 0.001 0.001 0.001 :0(setprofile)
100000 0.103 0.000 0.103 0.000 :0(sin)
1 0.207 0.207 0.766 0.766 iterations.py:19(test_for)
100000 0.268 0.000 0.472 0.000 iterations.py:4(<lambda>)
1 0.000 0.000 0.767 0.767 profile:0(<function test_for at 0x00A9D4B0>)
0 0.000 0.000 profile:0(profiler)


300003 function calls in 0.598 CPU seconds

Ordered by: standard name

ncalls tottime percall cumtime percall filename:lineno(function)
100000 0.101 0.000 0.101 0.000 :0(exp)
1 0.001 0.001 0.001 0.001 :0(setprofile)
100000 0.103 0.000 0.103 0.000 :0(sin)
1 0.122 0.122 0.597 0.597 iterations.py:26(test_for_smart)
100000 0.270 0.000 0.475 0.000 iterations.py:4(<lambda>)
1 0.000 0.000 0.598 0.598 profile:0(<function test_for_smart at 0x00A9D4F0>)
0 0.000 0.000 profile:0(profiler)


Итого: map и LC практически дают одно и то же (формально LC даже проигрывает 4ms, хотя эта разница уже в рамках погрешности), for с append-ом резко отстает, for без append-а —
тоже тормознее, хотя и не так сильно
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.