【问题标题】:How do I generate a rule for more than one option in Bogus?如何在 Bogus 中为多个选项生成规则?
【发布时间】:2021-04-26 02:24:30
【问题描述】:

我有一个随机选择一个选项的规则:

    .RuleFor(c=>field, x=>x.PickRandom("Option1", "Option2", "Option3", "Option4"))

使用默认值,我可以更改其中一项的概率。我想设置所有四个项目的概率。选项 1 的选择率为 50%,选项 2 的选择率为 30%,选项 3 为 15%,选项 4 为 5%。

我想使用 WeightedRandom:

    .RuleFor(c=>field, x=>PickWeightedRandom(valueArray, weightArray)

没有 PickWeightedRandom 这样的方法,但是 WeightedRandom 是 Randomizer 类中的一个方法。如何让 WeightedRandom 工作?

编辑:也许是一种扩展方法?

【问题讨论】:

    标签: c# testing data-generation bogus


    【解决方案1】:

    一个答案是在其他地方选择随机字符串,然后使用 => 运算符指向结果。

        public static string PickAString(string[] items, float[] weights)
        {
            // hopefully all the weights will add up to 1. If not, this method may throw for array out of bounds.
            // Also, it would be best if the number of items in each array is the same, to prevent out of bounds exception.
    
            // generate a number from 0 to less than 1
            double randomValue = random.NextDouble();
            double weightSum = 0;
            for (int i = 0; i < items.Length; i++)
            {
                weightSum += weights[i];
                if (randomValue < weightSum)
                    return items[i];
            }
            return null; // if the weights don't add up.
        }
    

        .RuleFor(c => c.field, _ =>
        { 
            return PickAString(values, weights); 
        }) 
    

    这可行,但将其添加到库中会更优雅。

    【讨论】:

      【解决方案2】:

      以下似乎有效:

      void Main()
      {
         var items = new []{"kiwi", "orange", "cherry", "apple"};
         var weights = new[]{0.1f, 0.1f, 0.2f, 0.6f};
         
         var faveFaker = new Faker<Favorite>()
            .RuleFor(x => x.Fruit, f => f.Random.WeightedRandom(items, weights));
            
         faveFaker.Generate(10).Dump();
      }
      
      public class Favorite
      {
         public string Fruit {get;set;}
      }
      
      


      当然,使用 C# 扩展方法始终是扩展 Bogus 以最适合您的 API 需求的绝佳方式:

      void Main()
      {  
         var faveFaker = new Faker<Favorite>()
            .RuleFor(x => x.Fruit, f => f.WeightedRandom( ("kiwi",   0.1f), ("orange", 0.1f),
                                                          ("cherry", 0.2f), ("apple",  0.6f)) );
            
         faveFaker.Generate(10).Dump();
      }
      
      public class Favorite
      {
         public string Fruit {get;set;}
      }
      
      public static class MyExtensionsForBogus
      {
         public static T WeightedRandom<T>(this Faker f, params (T item, float weight)[] items)
         {
            var weights = items.Select(i => i.weight).ToArray();
            var choices = items.Select(i => i.item).ToArray();
            return f.Random.WeightedRandom(choices, weights);
         }
      }
      

      【讨论】:

        猜你喜欢
        • 2021-09-11
        • 2021-04-29
        • 2016-03-10
        • 2018-02-15
        • 1970-01-01
        • 2022-01-05
        • 2016-08-22
        • 2018-10-05
        • 2014-05-12
        相关资源
        最近更新 更多