2013-07-23 5 views
4

Я получаю последовательность записей из файла CSV. Я хочу опционально фильтровать эти записи по дате и типу и, возможно, консолидировать записи, соответствующие определенным критериям. При необходимости фильтрация по дате и типу осуществляется с использованием Seq.filter. Однако я хотел бы дополнительно объединить записи, соответствующие определенным критериям. У меня есть работающая функция, я просто не могу понять, как ее можно применить к полученной последовательности. Я не могу использовать Seq.filter, потому что консолидация работает во всей последовательности не по одному элементу за раз. Я могу решить это с помощью промежуточной переменной, мне просто интересно, был ли изящный идиоматический способ справиться с этим.Условный фильтр в прямом трубопроводе в F #?

В принципе, я хочу знать способ условного применения одной (или более) частей цепи в прямой последовательности труб.

Это то, что я хочу в псевдокоде (options имеет параметры командной строки):

let x = 
    getRecords options.filePath 
    |> Seq.filter (fun r -> if options.Date.HasValue then 
          r.Date.Date = options.Date.Value.Date else true) 
    |> Seq.filter (fun r -> if not(String.IsNullOrEmpty(options.Type)) then 
          r.Type = options.Type else true) 
    if options.ConsolidateRecords then 
     |> consolidateRecords 

ответ

7

Вы можете использовать if ... else выражение с функцией идентификации в else статья:

let x = 
    getRecords options.filePath 
    |> (* ... bunch of stuff ... *) 
    |> (if options.ConsolidateRecords then consolidateRecords else id) 
    |> (* ... optionally more stuff ... *) 
5

Я хотел бы сделать что-то вроде

let x = 
    getRecords options.filePath 
    |> Seq.filter (fun r -> if options.Date.HasValue then 
          r.Date.Date = options.Date.Value.Date else true) 
    |> Seq.filter (fun r -> if not(String.IsNullOrEmpty(options.Type)) then 
          r.Type = options.Type else true) 
    |> fun x -> 
     if options.ConsolidateRecords then x |> consolidateRecords 
     else .... 
+0

Мне это нравится. Так что ничего не делать, когда 'options.ConsolidateRecords' false, тогда предложение else просто вернет' x'? Или у вас было что-то еще? – User

+2

Вы хотите сделать снимок экрана своего 7777 баллов, прежде чем я это сделаю? Я чувствую себя неплохо, выставляя его lol – User

+0

@User Либо верните x, либо продолжите обработку, в зависимости от того, что вы в противном случае сделали бы. – mydogisbox

3

Вы также можете скрыть предыдущее определение x:

let x = 
    getRecords options.filePath 
    |> Seq.filter (fun r -> 
     not options.Date.HasValue || r.Date.Date = options.Date.Value.Date) 
    |> Seq.filter (fun r -> 
     String.IsNullOrEmpty(options.Type) || r.Type = options.Type) 
let x = if options.ConsolidateRecords then consolidateRecords x else x 
Смежные вопросы