我定義了一個包含少數自定義生成器的類型,以使FsCheck生成幾種類型的自定義實例。但對於其中一種複雜類型,我想先使用默認的FsCheck生成,然後調整結果。這裏有一個(簡化)代碼:從相同類型的自定義生成器中調用默認FsCheck生成器
type CustomGenerators =
static member FirstCustomType() = /* function that returns FirstCustomType */
static member SecondCustomType() =
Arb.generate<SecondCustomType>
|> Gen.map (fun x -> /* adjust some data in the generated instance */)
|> Arb.fromGen
的問題是,當SecondCustomType()靜態方法調用Arb.generate它立即調用SecondCustomType()引起無限遞歸。我知道Arb.generate必須尊重自定義生成器,所以這就是爲什麼它調用靜態SecondCustomType(),但我需要調用SecondCustomType的默認(不自定義)Arb.generate實現。由於我的自定義生成器使用FirstCustomType的自定義生成器,所以我無法調用其他類型的實現,因此默認的SecondCustomType實現必須知道CustomGenerators類型中定義的所有自定義生成器。這是一個壞圈,我還沒有找到一個乾淨的決議(只有解決方法)。
爲了測試,我建議在''SecondCustomTypeTestWrapper''中爲''SecondCustomType''封裝一個簡單的包裝器,定義該包裝器的定製生成器,而不是'SecondCustomType'本身,並讓你的測試將包裝器作爲參數。 –
是的,這是我已經做了,但我想知道沒有額外的類型包裝是否有更好的方法。 –
而不是立即在靜態類中定義arbitraries,難道你不能定義一些返回gen值的正常F#函數,然後在你需要它們時編寫它們嗎?這就是我通常所做的,但是我從來沒有使用靜態的基於會話的類... –