Тогда я не вполне понял, в чём преимущество. Либо пользователю надо знать, с какой имплементацией он работает, и тогда он будет явно обращаться к core.crystal_ball_reader, либо мы этот выбор делаем за него заранее, и тогда внутри core/__init__.py у нас будет строка вида from .readers import crystal_ball_reader as reader . Вариант с инжекцией в глобальное пространство имён, по сути, эквивалентен второму варианту, и не позволяет реализовать первый вариант без дополнительного уровня абстракции. Единственное, что мне приходит в голову, это ситуация, когда разные скрипты одного пользователя должны получать разные имплементации одного сервиса в зависимости от внешних факторов, что-то типа паттерна стратегия наоборот. Тогда логику выбора имплементации будет очень неудобно размещать в __init__.py, в отличие от предлагаемого вами подхода.
Если в API ядра не будет обратно-несовместимых изменений, то любой подход сойдёт. Если будут, пользователям придётся обновлять свои скрипты и придётся читать release notes - и тут будет проще найти те из них, в которых используется устаревшее API. Кроме того, "мы не видим скрипты пользователей" - это всё же перебор. Вы их видите, так как вы их исполняете. А потому можете проверить импорты и послать пользователю оповещение "вы используете API, которое мы сломаем через неделю, пните свой отдел разработки, чтобы они вовремя обновили скрипт". Это, наверно, можно реализовать и в случае инжекции, но не так легко, я полагаю.
Не спорю. Мой аргумент был, что пользователю ни в одном из приведённых решений не требуется "знать устройство ядра и постоянно использовать это знание". А потому это не аргумент в пользу выбранного варианта (как и любого другого, впрочем).
Можно и так, да. Но модули уже предлагают готовый естественный способ группировки функций, не имеющих общего состояния, так что если у пользователя есть доступ к модулю (как, скажем, при импорте), группировка в неймспейс уже реализована без нужды в отдельном классе. Хотя соглашусь, это не очень большое преимущество.
Мы привязываемся к конкретной реализации сервиса, что допустимо только в случае, если она единственная и неизменяемая.
Пользователь вынужден каждый раз повторять заклинание импорта.
Пользователь должен знать устройство ядра и постоянно использовать это знание, что приводит к трудностям при рефакторинге ядра.
Совершенно не факт. Никто не мешает начать экспортировать из ядра новую реализацию, до тех пор, пока эта реализация не нарушает контракт предыдущей. А если нарушает, то ни один из вариантов не поможет, придётся переписывать пользовательский код.
Мы можем по импортам сразу понять, затронут ли пользовательский код изменениями в ядре. Вариант с инъекцией в глобальное пространство имён по сути эквивалентен from core import *.
Пользователь должен знать видимый контракт ядра, а не его реализацию. И он должен знать контракт независимо от способа импорта. Не зная контракта, он не сможет пользоваться функциями ядра.
Ну и до кучи, только первый вариант позволяет удобно делить функции ядра на отдельные пространства имён.
Я бы поспорил, что для обучения программированию обязательно нужен язык со статической типизацией, и по возможности строгой. Если сразу не приучиться держать в уме "с каким типом данных я сейчас работаю? что он умеет?", то потом научиться этому сложнее. В таких языках на это есть обычно исчерпывающий ответ - объявление переменной. В сравнении с этим питон и js нередко оказываются в ситуации "ну тут из функции какая-то фигня приехала, у неё вроде есть вот такой метод, а вообще я фз что это". Собственно, type hints в питоне и typescript на это и нацелены.
В комментарии выше речь шла о личных потребностях. Условно, ну есть у тебя яхта с бассейном, в котором плавает яхта поменьше, а дальше что? =) Здесь и сейчас, с точки зрения индивида, колонии у других звёзд - это скорее понты, чем что-то, непосредственно нужное для выживания. Другое дело что понты понтам рознь, и от некоторых тоже есть польза... но далеко не ото всех.
Есть мнение, что да, ушли. Дальше, конечно, пересказ "как понял" - могу ошибаться.
Безумные мощности ядерных зарядов 70х объяснялись тем, что погрешность попадания измерялась чуть ли не в километрах - а против укреплённых целей близкое попадание и в километре это очень большая разница. Поэтому и приходилось делать заряды запредельной мощности, чтобы уж наверняка. А сейчас попасть могут чуть ли не в конкретный кирпич в стене, и избыточная мощность заряда стала просто не нужна. Опять же, можно громко говорить про успехи в сокращении ядерных вооружений, при этом не теряя в военном потенциале.
Так что есть вероятность, что после маштабной ядерной войны вместо полномасштабной ядерной зимы мы увидим "всего лишь" изрядный кусок загаженной территории, а основной ущерб будет от разрушения инфраструктуры и сопутствующего экономического и технологического развала - с "плюшками" вроде голода, эпидемий и прочего фаллаута ИРЛ, которые угробят больше народу, чем собственно ядерные удары.
Вообще я читал, что бактериофаги вроде довольно привередливые - многие "охотятся" только на определённые виды бактерий, и не трогают даже родственные виды. Но я не спец.
Я воспринимаю аннотации типов скорее как декларативное описание "что в этом параметре/этой переменной". Условно, код на C-подобном языке float speed содержит описание типа, но не содержит сведения о том, как это значение интерпретировать - как метры в секунду или как километры в час. Тут ближе подходит концепция доменных типов, конечно - но аннотации в питоне являются приемлемым промежуточным решением, и позволяют добиться хоть какой-то ясности, не трогая саму логику.
Что касается вышеупомянутой проблемы со словарями - есть TypedDict, который позволяет, по сути, описать схему для словаря (по аналогии со схемой JSON).
Ну тут много "но"... 1. "точно в цель" - это не так-то просто. Особенно на легоньком дроне, которого будет колбасить морской ветер. 2. Далеко ли улетит такой дрон? А значит, нужно средство доставки на дистанцию поражения. А оно, скорее всего, будет больше и заметнее, и может быть подбито до выпуска дронов. 3. Радар, способный заметить ракету на дистанции поражения - не пожжёт ли электронику таких дронов? А экранирование тоже имеет вес... Так что да, штука потенциально уязвимая, но не более уязвимая, чем, скажем, AEGIS крейсер. Силы прикрытия для того и существуют, в общем-то.
Никто ни от чего не защищён. Вопрос уже давно стоит не столько "что ты делаешь", сколько "кому ты попадёшься под горячую руку", что в реале, что в инете. И чем дальше, тем больший будет маразм, потому что, упрощённо говоря, у принимающих решения маразм теперь входит в KPI. Не юродствуешь - значит, ненадёжен.
Retrieval Augmented Generation? Тут нужна модель с большим окном контекста, как минимум. Обычные модели под такую задачу подходят довольно плохо. Да и запуск такой модели на оборудовании клиента будет тем ещё удовольствием.
Ну по мне так это было бы интереснее, чем завязываться на OpenAI.
А если не использовать OpenAI, что изменится?
Хммм. Ну ладно, может, я просто не очень чётко представляю набор требований к такой системе. Спасибо за дискуссию. =)
Тогда я не вполне понял, в чём преимущество. Либо пользователю надо знать, с какой имплементацией он работает, и тогда он будет явно обращаться к
core.crystal_ball_reader
, либо мы этот выбор делаем за него заранее, и тогда внутриcore/__init__.py
у нас будет строка видаfrom .readers import crystal_ball_reader as reader
. Вариант с инжекцией в глобальное пространство имён, по сути, эквивалентен второму варианту, и не позволяет реализовать первый вариант без дополнительного уровня абстракции. Единственное, что мне приходит в голову, это ситуация, когда разные скрипты одного пользователя должны получать разные имплементации одного сервиса в зависимости от внешних факторов, что-то типа паттерна стратегия наоборот. Тогда логику выбора имплементации будет очень неудобно размещать в__init__.py
, в отличие от предлагаемого вами подхода.Если в API ядра не будет обратно-несовместимых изменений, то любой подход сойдёт. Если будут, пользователям придётся обновлять свои скрипты и придётся читать release notes - и тут будет проще найти те из них, в которых используется устаревшее API. Кроме того, "мы не видим скрипты пользователей" - это всё же перебор. Вы их видите, так как вы их исполняете. А потому можете проверить импорты и послать пользователю оповещение "вы используете API, которое мы сломаем через неделю, пните свой отдел разработки, чтобы они вовремя обновили скрипт". Это, наверно, можно реализовать и в случае инжекции, но не так легко, я полагаю.
Не спорю. Мой аргумент был, что пользователю ни в одном из приведённых решений не требуется "знать устройство ядра и постоянно использовать это знание". А потому это не аргумент в пользу выбранного варианта (как и любого другого, впрочем).
Можно и так, да. Но модули уже предлагают готовый естественный способ группировки функций, не имеющих общего состояния, так что если у пользователя есть доступ к модулю (как, скажем, при импорте), группировка в неймспейс уже реализована без нужды в отдельном классе. Хотя соглашусь, это не очень большое преимущество.
Я бы поспорил, что первый вариант лучше.
Совершенно не факт. Никто не мешает начать экспортировать из ядра новую реализацию, до тех пор, пока эта реализация не нарушает контракт предыдущей. А если нарушает, то ни один из вариантов не поможет, придётся переписывать пользовательский код.
Мы можем по импортам сразу понять, затронут ли пользовательский код изменениями в ядре. Вариант с инъекцией в глобальное пространство имён по сути эквивалентен from core import *.
Пользователь должен знать видимый контракт ядра, а не его реализацию. И он должен знать контракт независимо от способа импорта. Не зная контракта, он не сможет пользоваться функциями ядра.
Ну и до кучи, только первый вариант позволяет удобно делить функции ядра на отдельные пространства имён.
Вступление есть, а где статья? Кейс подразумевает разбор конкретного случая всё-таки.
Напомнило, как один из студентов сдал отчёт по прохождению практики из одной строчки "Что делал - под NDA, рассказать не могу."
Я бы поспорил, что для обучения программированию обязательно нужен язык со статической типизацией, и по возможности строгой. Если сразу не приучиться держать в уме "с каким типом данных я сейчас работаю? что он умеет?", то потом научиться этому сложнее. В таких языках на это есть обычно исчерпывающий ответ - объявление переменной.
В сравнении с этим питон и js нередко оказываются в ситуации "ну тут из функции какая-то фигня приехала, у неё вроде есть вот такой метод, а вообще я фз что это". Собственно, type hints в питоне и typescript на это и нацелены.
Слишком уж правдоподобно. Как-то смеяться не хочется.
А что-то стоящее и не впихнуть в минутное вертикальное видео.
Удивлён, что кто-то Shorts использует. Очень много вопросов в сети "как убрать Shorts из Youtube".
В комментарии выше речь шла о личных потребностях. Условно, ну есть у тебя яхта с бассейном, в котором плавает яхта поменьше, а дальше что? =)
Здесь и сейчас, с точки зрения индивида, колонии у других звёзд - это скорее понты, чем что-то, непосредственно нужное для выживания.
Другое дело что понты понтам рознь, и от некоторых тоже есть польза... но далеко не ото всех.
Потребности - не беспредельны, а вот понты - очень даже. Достаточно посмотреть на Дубай. =)
Есть мнение, что да, ушли. Дальше, конечно, пересказ "как понял" - могу ошибаться.
Безумные мощности ядерных зарядов 70х объяснялись тем, что погрешность попадания измерялась чуть ли не в километрах - а против укреплённых целей близкое попадание и в километре это очень большая разница. Поэтому и приходилось делать заряды запредельной мощности, чтобы уж наверняка.
А сейчас попасть могут чуть ли не в конкретный кирпич в стене, и избыточная мощность заряда стала просто не нужна. Опять же, можно громко говорить про успехи в сокращении ядерных вооружений, при этом не теряя в военном потенциале.
Так что есть вероятность, что после маштабной ядерной войны вместо полномасштабной ядерной зимы мы увидим "всего лишь" изрядный кусок загаженной территории, а основной ущерб будет от разрушения инфраструктуры и сопутствующего экономического и технологического развала - с "плюшками" вроде голода, эпидемий и прочего фаллаута ИРЛ, которые угробят больше народу, чем собственно ядерные удары.
Вообще я читал, что бактериофаги вроде довольно привередливые - многие "охотятся" только на определённые виды бактерий, и не трогают даже родственные виды. Но я не спец.
Я воспринимаю аннотации типов скорее как декларативное описание "что в этом параметре/этой переменной". Условно, код на C-подобном языке
float speed
содержит описание типа, но не содержит сведения о том, как это значение интерпретировать - как метры в секунду или как километры в час. Тут ближе подходит концепция доменных типов, конечно - но аннотации в питоне являются приемлемым промежуточным решением, и позволяют добиться хоть какой-то ясности, не трогая саму логику.Что касается вышеупомянутой проблемы со словарями - есть TypedDict, который позволяет, по сути, описать схему для словаря (по аналогии со схемой JSON).
И ведь всё равно не поможет. Прогнулся - значит, будут давить ещё сильнее.
Конкретных примеров атак нет. Примеров их исполнения тоже нет.
Без этого - статья на уровне "вирусы, спамы, куки".
Ну тут много "но"...
1. "точно в цель" - это не так-то просто. Особенно на легоньком дроне, которого будет колбасить морской ветер.
2. Далеко ли улетит такой дрон? А значит, нужно средство доставки на дистанцию поражения. А оно, скорее всего, будет больше и заметнее, и может быть подбито до выпуска дронов.
3. Радар, способный заметить ракету на дистанции поражения - не пожжёт ли электронику таких дронов? А экранирование тоже имеет вес...
Так что да, штука потенциально уязвимая, но не более уязвимая, чем, скажем, AEGIS крейсер. Силы прикрытия для того и существуют, в общем-то.
Никто ни от чего не защищён. Вопрос уже давно стоит не столько "что ты делаешь", сколько "кому ты попадёшься под горячую руку", что в реале, что в инете. И чем дальше, тем больший будет маразм, потому что, упрощённо говоря, у принимающих решения маразм теперь входит в KPI. Не юродствуешь - значит, ненадёжен.
Retrieval Augmented Generation? Тут нужна модель с большим окном контекста, как минимум. Обычные модели под такую задачу подходят довольно плохо. Да и запуск такой модели на оборудовании клиента будет тем ещё удовольствием.