Функции, не входящие в диапазон - PullRequest
5 голосов
/ 06 октября 2010

У меня есть класс, для которого я реализую диапазоны.Я хотел бы реализовать функции так, как это делает библиотека Фобоса, то есть вне основного класса.

void popBack(T)(ref T[] a) if (!is(Unqual!T == char) && !is(Unqual!T == wchar))
{
    assert(a.length);
    a = a[0 .. $ - 1];
}

Вот моя версия:

void popFront(T)(ref PersistentList!(T) a)
{
    a = a.next();   
}

Когда я пытаюсь скомпилировать этот код с forech, я получаю:

Error   1   Error: no property 'popFront' for type 'stmd.PersistentList!(int).PersistentList'   main.d  

Я могу переместить участникакод в основной класс, но так как я изменяю входное значение "ref", я не могу использовать popFront (), мне действительно нужен popFront (ref a).

Что я делаю не так?

Ответы [ 2 ]

4 голосов
/ 06 октября 2010

То, что вы пытаетесь сделать, зависит от того, что сообщество D называет унифицированным синтаксисом вызова функций.Это возможность вызывать функции, не являющиеся членами, с тем же синтаксисом, что и функции-члены.Это было реализовано для массивов только в течение длительного времени, и были некоторые споры о том, как далеко это сделать.Было решено, что это должно быть реализовано для всех типов, но Уолтер Брайт, разработчик компилятора, еще не удосужился сделать это, потому что он лихорадочно работает над поддержкой 64-бит.

Унифицированный синтаксис вызова функцииописано в книге Андрея Александреску « Язык программирования D », которая считается авторитетным руководством по D2.В настоящее время отсутствие реализации считается ошибкой.Это должно быть исправлено в нескольких выпусках.

3 голосов
/ 06 октября 2010

Фобос реализует только функции диапазона вне структуры / класса для массивов.Массивы позволяют вам вызывать функции на них, как если бы они были функциями-членами.Итак, если у вас есть эта функция:

int func(int[] arr)
{
    return arr[0];
}

, вы можете назвать ее так:

auto arr = [1, 2, 3];
auto val = arr.func();

вместо

auto val = func(arr);

Возможность сделать это со всемиТипы называются универсальным синтаксисом вызова функции, но в настоящее время это недопустимо в D, хотя похоже, что, вероятно, оно будет добавлено.

На самом деле нет причин объявлять ваши функции диапазона за пределами вашего типа диапазона, если только выВы хотите поделиться этой реализацией с другими типами диапазонов, что часто в любом случае было бы невозможно, поскольку внутренняя реализация имеет дело с тем, как тип контейнера поддерживает свои данные.Таким образом, вы можете просто сделать их частью вашего типа диапазона.Это то, что делает Фобос во всех случаях, кроме массивов, которые, очевидно, не могут иметь их как часть своего типа и должны использовать свою способность вызывать функции, как если бы они были функциями-членами, чтобы это работало.

...