2011-01-12 2 views
0

Я писал несколько F # сейчас около 6 месяцев, и я столкнулся с каким-то поведением, которое я не могу объяснить. У меня есть код с коротким кодом ниже. (имена значений были изменены, чтобы защитить невиновных!)F # - странное поведение при сопоставлении шаблонов с дискриминационными объединениями

У меня есть иерархия, определяемая с использованием типов записей rec1 и rec2, а также тип объединенного объединения с возможными значениями CaseA и CaseB. Я вызываю функцию ('mynewfunc'), которая принимает тип опции du_rec. Внутренне эта функция определяет рекурсивную функцию, которая обрабатывает иерархию.

Я начинаю обработку, передавая значение параметра None для представления корня иерархии (на самом деле эта функция десериализует иерархию из файла).

Когда я запускаю приведенный ниже код, я нахожу строку «failwith» invalid parent ». Я не могу понять, почему это так, потому что значение None, которое передается, должно соответствовать внешнему шаблону «Нет».

Код работает, если я удаляю один из наборов комментариев. Это не остановит всю работу для меня - я просто чувствую себя немного неловко, не зная, почему это происходит (я думал, что понимание F #)

Заранее спасибо за любые ответы

Джеймс

type rec2 = 
    { 
    name : string 
    child : rec1 option 
    } 
and rec1 = 
    { 
    name : string ; 
    child : rec2 option 
    } 
and du_rec = 
    | Case1 of rec1 
    | Case2 of rec2 


let mynewfunc (arg:du_rec option) = 
    let rec funca (parent:du_rec option) = 
     match parent with 
     | Some(node) -> 
      match node with 
      | Case2(nd) -> 
       printfn "hello" 
      (* | Case1(nd) -> 
       printfn "bye bye" *) 
      | _ -> 
       failwith "invalid parent" 
     | None -> 
       // printfn "case3" 
       () 
     funcb(None) 
    and funcb (parent: du_rec option) = 
     printfn "this made no difference" 
    let node = funca(arg) 
    () 

let rootAnnot = mynewfunc(None) 
+0

Вам не нужно использовать 'and' с du_rec. Не уверен, что это помогает. – gradbot

+3

Исходный код был немного искажен и не компилировался. Я исправил его, чтобы он компилировался. Я также тестировал его на своей машине, он работает нормально. Можете ли вы описать среду, в которой вы используете (возможно, моно?) С номерами номеров F # и FSI? – Juliet

+0

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

ответ

3

Основываясь на комментариях, это всего лишь плохой опыт в отладчике (где подсветка предполагает, что поток управления идет туда, где это не так); код делает то, что вы ожидаете.

(Есть целый ряд мест, где F # компилятор может улучшить свои порядковые-очки генерироваться в PDB-файлы, чтобы улучшить опыт отладки;. Я думаю, что мы будем смотреть на это в будущем выпуске)

+0

благодарит Брайана, следующий код еще короче, а также смущает отладчик: матч 2 с | 1 -> printfn "one" | _ -> () – Jimmy

Смежные вопросы