F #: зачем иметь и «::», и «@» - PullRequest
0 голосов
/ 23 мая 2018

Я недавно начал читать о F #, и, очевидно, очень скоро я получил один вопрос новичка.Речь идет о списках (коллекциях).

Согласно руководствам F #, для создания списков есть две операции: они являются минусами (иначе говоря, ::) и @.Учитывая тот факт, что @ является более универсальным (может объединять подсписки, а не отдельные элементы, а также может добавляться в хвост, в отличие от операции cons), мой вопрос: в какой ситуации мы должны использовать точно:: вместо @, чтобы избежать двусмысленности или нежелательных побочных эффектов и так далее?

Другими словами: :: теоретически избыточен или нет?

Ответы [ 3 ]

0 голосов
/ 23 мая 2018

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

Я бы сказал, что было бы лучше, если бы он вышел на пенсию, и вместо него рекомендовалось бы использовать List.append.

Сегодняшнее положение вещей таково, что @ определяется в prim-types.fs в качестве эквивалента следующей функции:

let rec (@) x y = 
    match x with 
    | [] -> y 
    | (h::t) -> h :: (t @ y)

и позже переэкспонирован как List.append:

let append list1 list2 = list1 @ list2

Существует очень мало причин, по которым он должен быть представлен как оператор, в первую очередь, кроме "OCaml делает это".

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

Таким образом, @ является чисто образовательным - кажется, что он существует только для того, чтобы запутать новичков вязык (или напомните им, что следует помнить о характеристиках производительности структур данных, которые они используют).

0 голосов
/ 31 мая 2018

Это две разные функции с двумя поведениями, которые можно использовать для создания списка.

:: operator добавить элемент в список @ объединить два списка

добавить элемент по одномуодин легко со списком.Объединение двух списков требует больше работы.

Лучше использовать :: operator, и Забронировать @ operator только для слияния.

0 голосов
/ 23 мая 2018

Тип list имеет два конструктора: [] и ::.Если удалить ::, останется только конструктор [], что сделает невозможным создание непустых списков.

Обратите внимание, что что-то вроде [1;2;3] является синтаксическим сахаром для 1::2::3::[], поэтомуполагается на существование ::.

Аналогично, @ - это функция, которая определена с использованием ::, поэтому, если :: не существует, то и 10101 *.

* не может.1018 * Обратите внимание, что @ не подходит в качестве замены :: в определении list, поскольку, если у вас еще нет способа создания непустых списков, @ не может бытьиспользуется для их создания ([] @ [] по-прежнему пустой список).

И даже если вы добавите конструктор для списков из одного элемента, @ приведет к неоднозначному представлению, поскольку можно представить [1;2;3]либо как ([1] @ [2]) @ [3], либо как [1] @ ([2] @ [3]) (плюс, вы можете просто добавить @ [] в любом месте).Таким образом, вы получите несколько разных представлений для семантически эквивалентных списков.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...