представьте что-то вроде этого:
import class B.*;
interface A supports A.testSum
{
int sum( int a , int b ) access from B.calculator;
testSum() { Assert(sum(1,1)==2); }
........
class B ...
{
void calculator() { A.sum(3,5); //ok }
void someOtherMethod() { A.sum(0,3); //compile error }
идея «опор» вторична, но актуальна, поскольку в этом случае тест применяется к интерфейсу (поэтому язык будет различать тест интерфейса, которыйвсе реализации должны пройти и тест реализации, который является специфическим для приватности реализации
, но важная идея, которую я хочу передать здесь, - это семантика контроля доступа; обратите внимание, что A.sum с ключевым словом «access from» может толькобыть вызван из метода B.calculator. Все остальное обнаруживается как ошибка времени компиляции. Идея здесь состоит в том, чтобы обеспечить архитектурные ограничения более детальным способом. Если вы не добавили «доступ из» или просто добавили «доступ из»* "это будет означать поведение по умолчанию, позволяющее вызывать метод из любой точки мира. Какие архитектурные ограничения? Хорошо, тот тип, который принудительно применяется вручную при создании многоуровневого проекта: слой A (самый низкий уровень) используется из слоя B (промежуточный уровень), который в свою очередь используется изслой С (высокий уровень).Но уровень B недоступен из уровня A, а уровень C недоступен ни из A, ни из B, но в противном случае он является общедоступным (это может быть то, к чему у конечного пользователя будет прямой доступ)
вопрос:знаете какой-нибудь язык (включая промежуточные языки от источника к источнику), который поддерживает вышеуказанную семантику?дополнительные вопросы для обсуждения, будет ли этот вид семантики контрпродуктивным, опасным или просто поощряющим плохой дизайн
Обновление: есть еще один действительно важный вариант использования для такого рода ограничений:
программирование, управляемое событиями: обычно проблема с событиями заключается в том, что события имеют тенденцию делать слишком много, и понимание цепочки зависимостей для событий может оказаться сложным
, поэтому, например, можно определить, что обработчик событийимеет только определенный набор видимых классов, с которыми он может взаимодействовать (или, наоборот, с определенным набором объектов, к которым он не может прикоснуться)