Проблемы создания записей с помощью FsCheck - PullRequest
1 голос
/ 31 октября 2019

Этот вопрос является продолжением предыдущего вопроса по с использованием FsCheck для создания записей . На исходный вопрос был дан хорошо составленный пример решения. Однако до того, как ответ был распространен, я попытался создать генератор, который включен ниже. К сожалению, сгенерированные записи type QueryRequest = {Symbol: string; StartDate: DateTime; EndDate: DateTime} имеют следующие проблемы:

  1. Отсутствует symbol
  2. Дата начала более ранняя, чем 1 января 2000 года
  3. Дата окончания позжечем 1 января 2019 года
Original:
{ Symbol = ""
  StartDate = 8/9/2057 4:07:10 AM
  EndDate = 10/14/2013 6:15:32 PM }
Shrunk:
{ Symbol = ""
  StartDate = 8/9/2057 12:00:00 AM
  EndDate = 10/14/2013 12:00:00 AM }

Поскольку я все еще нахожусь в процессе знакомства с F #, я был бы признателен за предложения / отзывы о том, как решать вышеупомянутые проблемыи возможности улучшения кода с точки зрения структуры, состава и т. д.

namespace Parser

module DataGenerators =
    open System
    open FsCheck

    type QueryRequest = {Symbol: string; StartDate: DateTime; EndDate: DateTime}

    type Tweet =
        static member GenerateRecords (year, month, day, symbol) =
            try
                let startDate = DateTime (year, month, day)                
                let endDate = startDate.AddDays 1.0
                Some {Symbol = symbol; StartDate = startDate; EndDate = endDate}
            with
            | :? ArgumentOutOfRangeException -> None

        static member Combine (years: int list) (months: int list) (days: int list) (symbols: string list) =
            let rec loop acc years months days symbols =
                match years, months, days, symbols with
                | [], [], [], [] -> acc
                | year :: years, month :: months, day :: days, symbol :: symbols -> loop ((year, month, day, symbol) :: acc) years months days symbols
                | _, _, _, _ -> acc

            loop [] years months days symbols

        static member Generate () =
            let years = Gen.choose (2000, 2019) |> Gen.sample 0 10
            let months = Gen.choose (1, 12) |> Gen.sample 0 10
            let days = Gen.choose(1, 31) |> Gen.sample 0 10
            let symbols = Gen.elements ["ORCL"; "IBM"; "AAPL"; "GOOGL"] |> Gen.sample 0 10

            Tweet.Combine years months days symbols
            |> List.map Tweet.GenerateRecords
            |> List.fold (fun acc r -> match r with Some q -> q :: acc | None -> acc) []

1 Ответ

0 голосов
/ 31 октября 2019

Я не могу воспроизвести вашу проблему, следующие значения true для 1000-х казней:

Tweet.Generate()
|> List.forall (fun q ->
    q.StartDate <= q.EndDate &&
    q.StartDate >= DateTime(2000, 1, 1) &&
    q.EndDate <= DateTime(2019, 12, 31) &&
    ["ORCL"; "IBM"; "AAPL"; "GOOGL"] |> List.contains q.Symbol)

Однако вы можете упростить Tweet, например, так:

type Tweet =
    static member GenerateRecords ((year, month, day), symbol) =
        try
            let startDate = DateTime (year, month, day)
            let endDate = startDate.AddDays 1.0
            Some {Symbol = symbol; StartDate = startDate; EndDate = endDate}
        with
        | :? ArgumentOutOfRangeException -> None

    static member Generate () =
        let years = Gen.choose (2000, 2019) |> Gen.sample 0 10
        let months = Gen.choose (1, 12) |> Gen.sample 0 10
        let days = Gen.choose(1, 31) |> Gen.sample 0 10
        let symbols = Gen.elements ["ORCL"; "IBM"; "AAPL"; "GOOGL"] |> Gen.sample 0 10
        let dates = List.zip3 years months days
        List.zip dates symbols
        |> List.choose Tweet.GenerateRecords
...