Pull to refresh

Comments 15

Я за S.O.L.I.D. поэтому считаю что данная функциональность будет только замедлять и нарушает OCP. Схожую функциональность можно элегантно реализовать через словари, а работают они быстрее чем множественные операторы сравнения.

В соответствующем PEP-0622 есть отличный пример:


if (
    isinstance(value, (list, tuple)) and
    len(value) > 1 and
    isinstance(value[-1], (Promise, str))
):
    *value, label = value
    value = tuple(value)
else:
    label = key.replace('_', ' ').title()

vs


match value:
    case [*v, label := (Promise() | str())] if v:
        value = tuple(v)
    case _:
        label = key.replace('_', ' ').title()

У второго варианта читаемость намного выше.


Причем здесь SOLID и OCP — непонятно, оба этих принципа никак не нарушаются. Словари, опять же, не всегда дают ту же выразительность, как pattern matching.

У второго варианта читаемость намного выше.
— не согласен,
[*v, label := (Promise() | str())] if v
— что здесь вообще происходит? :). В связке с моржовым оператором и | — стало супер не читабельно. Как будто это уже не Python а Haskell какой-нибудь.
Посмотрим.
Если можно будет делать что-то вроде такого:
elementsAreEqual = lambda aTuple:
    match aTuple:
    case (x,x): print("обе части одинаковы")
    case (_,_): print("обе части разные")

то это уже интереснее.

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


match aTuple:
    case (x,y) if x == y:
        ...

Я с большим скепсисом смотрел на эту фичу во время обсуждения. После появляения скепсис остался. Основная проблема — pattern matching не exhaustive. Дополнительные проблемы: т.к. типизация в рантайме, полный комплект runtime ошибок сохраняется в полный рост (включая has no attribute 'type' и т.д.). Сочетание интроспекции и возможность переопределять магические методы интроспекции ведёт к тому, что написанному верить очень трудно.


Вот, например, слегка модифицированный ваш код:


match media_object:
    case Video():
        raise ValueError("Не получается извлечь кадры из видео")
    case Image(type="jpg"):
        # Вернуть как есть
        return media_object
    case Image(type="png") | Image(type="gif"):
        return render_as(media_object, "jpg")

Вопрос: если type — это getter (декоратор @property), то когда он вызовется? Например, если media_object Video, будет ли вызван геттер?


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


Как если бы кто-то попытался из пластилина сделать проволочную модель (например, машинки). Пластилин очень плохо подходит для имитации проволоки. Очень плохо.

Меня как разработчика прототипов больше интересует удобочитаемость кода. Однако отсутствие механизма контроля над исчерпываемостью вариантов — озадачивает.

Ну, это и есть признак "мягкого языка". Утиная типизация (в отличие от системы трейтов, в том же Rust'е) не подразумевает полноты знания. Мы берём минимально возможное что нам нужно, игнорируя остальное. Как только мы говорим про "исчерпание", мы подразумеваем полное знание.

Эта разница больше кроется в интерпретации (Py) и компиляции (Rust). Просто тут можно было бы рассчитывать на большую строгость, т.к. речь скорее идет о логике.

Метод реализации (компиляция или интерпретация) тут вторичен. Основное — разное отношение к строгости. В питоне строгость минимальна (но она есть, в отличие от безумий php или js), в Rust — максимальна. (оба слова не оценивающие, а квалифицирующие). Питон проверяет только то, что нужно для выполнения операции, Rust проверяет всё (почти всё, но то, что он не проверяет — это временные недостатки языка). Соответственно, в рамках этой модели Питон не может проверить exhaustive, а Rust — может.


Точнее, питон мог бы поднимать ValueError, если не сработал ни один case в runtime, но это сильно бы противоречило духу написанного (расширенный if).


В целом, моё мнение, конструкция сыровата и дзен питона подмывает.

Такова воля создателя (языка) )

match уже без Гуидо делали.

Fast-forward to 2020, and Guido van Rossum, the creator of Python, committed the first documentation showing the new switch-statements, which have been named Structural Pattern Matching, as found in PEP 634.
Sign up to leave a comment.

Articles