2012-07-02 8 views
2

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

let inline (=~=) x y = abs x-y < 1.E-10 

Однако оператор не отображается на, скажем, списки

let test = [1;2] =~= [1;2] //---> error 

Можно ли объявить этот оператор течь как (=)?

Или это потребует, чтобы определить новые черты, как «StructuralEquality-ishness"?

Что лучше определить новый оператор, скажем, http://code.google.com/p/fsharp-typeclasses/?

+0

Да, но вы не можете редактировать Тип списка - он уже определен. Вы можете проверить (с помощью ':?'), Если тип - это список, и если это так, используйте свое собственное определение, но в F # нет классов типов. –

ответ

5

Я не знаю Unquote, но относительно приближенной функции/оператора Я не уверен, есть ли способ реализовать его со структурным сравнением.

Если вы хотите, чтобы сделать это «вручную», используя метод (или трюк), аналогичный тому, который используется для F # Классы типов проекта, вот пример:

type Approximate = Approximate with 
    static member inline ($) (Approximate, x:^n  ) = fun (y:^n) -> float (abs (x-y)) < 1.E-10 
    static member inline ($) (Approximate, x:list< ^n>) = 
     fun (y:list< ^n>) -> 
      x.Length = y.Length && (List.zip x y |> List.forall (fun (a,b) -> (Approximate $ a) b)) 
// More overloads 
let inline (=~=) x y = (Approximate $ x) y 
+0

Очень хорошо. для моего назидания, ваша библиотека содержит биты, которые уже более или менее соответствовали бы этому? – nicolas

+0

Этот проект - всего лишь демонстрационный проект. Цель состояла в том, чтобы показать технику, а не использовать ее в производстве (хотя я не вижу никаких проблем с этим). Вам не нужно связывать его только для реализации этого, ни один из определенных там спецификаций не поможет в этом конкретном случае, но если вас интересует эта техника, это хорошая ссылка. – Gustavo

3

(я не использовал Unquote так это может быть не применимо.)

Посмотрите на подпись вашей функции

'a -> 'b -> bool (requires member (-) and member Abs) 

List лань sn't поддерживают любой из этих операторов. Да, ваша функция является общей, но ограничения исключают ее использование со списками.

(=), с другой стороны, не имеет ограничений, то есть его можно использовать с любым типом. Если ваша функция может быть переписана, чтобы удалить ограничения, то ее можно использовать аналогичным образом (но я не вижу, как это возможно, учитывая использование - и abs - как вы ожидаете, что list будет вести себя с этими операторами?).

+0

= имеет ограничения: Equality – nicolas

+0

Я не ожидаю, что этот оператор будет работать, как есть, но его модифицированная версия. вопрос заключается в том, как поднять этот оператор самым общим образом. результирующий оператор в списке потребует, чтобы его элементы удовлетворяли указанным ограничениям и приводили список результатов, полученных приложением исходного оператора, к каждому элементу обоих списков, например – nicolas

+0

@nicolas: Хорошая точка, но равенство равно довольно слабое ограничение, учитывая каждый тип, но те, которые украшены '[]' удовлетворяют его. – Daniel