生成随机输出,并在运行时定义和更改种子值

时间:2016-09-06 19:51:50

标签: c# wpf random

我在C#中编写一个随机名称生成器。 它是用Visual Studio 2015编写的WPF应用程序。

WPF窗口截图说明:

A WPF Window screenshot to illustrate

当我尝试从运行时用户设置的种子值生成名称时,会出现问题。之前,我有随机方法,提供所有生成逻辑的名称,声明为静态,种子值在程序运行的整个时间内保持不变。这很有效,每次单击Generate Name按钮时都会产生不同的输出。

但是,我希望在程序运行时添加更改内置随机方法的种子数的功能。为了做到这一点,我不得不将声明更改为非静态,并将Random作为NamesGenerator对象实例的一部分。现在,每次更改种子值时,都会创建一个不同的名称,但是当我将种子值保持不变时,每次单击Generate Name按钮都会创建相同的输出。 (您可以在WPF窗口截图中看到这一点。)

我最终想要的是一个可以生成相同输出的程序(因此我使用的是种子值),但我希望每个种子值都有一组可用的名称(因为有随机的时候)方法是静态的)不只是一直生成一个名称。

我不确定这是否可行,如果是的话,现在显然不在我的联盟中,这就是我寻求帮助的原因。我试图在网上搜索类似的问题和SO,但我找不到任何有用的东西。

在这里,我提供了一些代码:

class NamesGenerator
{
   Random randomNumber; //I tried to have this static and non-static, to no avail

...NAMES GENERATING CODE...

   //SetSeedValue is called from the WPF Window and instantiates a new Random instance with seed value. 
   public void SetSeedValue(int seedValue)
        {
            randomNumber = new Random(seedValue); 
        }
   public string GenerateName()
    {
        // determines if the name is male or female (unlike in English, there is a whole lot of differences in Russian related to this)
        bool genderValue = equalDistributionMechanism(); // returns true if the name is masculine, false if it is not

        string name;

        name = makeTestName((randomNumber.Next(1, 2)), genderValue); //first name

        name += " " + makeTestName((randomNumber.Next(1, 2)), genderValue) 
               + addSuffix((randomNumber.Next(1, 7)), gender: genderValue); //last name

            return name;
        }

我对如何解决我的问题的想法是检查randomNumber是否已经使用给定的seedValue实例化,如果是,则不在SetSeedValue方法中创建randomNumber的另一个实例,但我不知道如何检查这个

我正在使用的WPF代码:

public partial class MainWindow : Window
{
    NamesGenerator namesGenerator = new NamesGenerator();

    public MainWindow()
    {
        InitializeComponent();
    }

    private void GenerateNameButton_Click(object sender, RoutedEventArgs e)
    {
        int seedValue;

        try
        {
            seedValue = int.Parse(SeedNumberTextBox.Text);
        }
        catch
        {
            MessageBox.Show("Not a valid seed number. Try again.", "Invalid Seed Number", MessageBoxButton.OK, MessageBoxImage.Warning);
            return;
        }

        namesGenerator.SetSeedValue(seedValue);
        AddNewName(namesGenerator.GenerateName());
    }
}

感谢您的时间以及如何实现这一目标的任何想法:)。

修改 由于HüseyinBurakKaradag的请求,添加了GenerateName方法。

1 个答案:

答案 0 :(得分:1)

在您编辑问题之前,您有:

private void GenerateNameButton_Click(object sender, RoutedEventArgs e)
    {
        int seedValue;

        try
        {
            seedValue = int.Parse(SeedNumberTextBox.Text);
        }
        catch
        {
            MessageBox.Show("Not a valid seed number. Try again.", "Invalid Seed Number", MessageBoxButton.OK, MessageBoxImage.Warning);
            return;
        }

        namesGenerator.SetSeedValue(seedValue);
        AddNewName(namesGenerator.GenerateName());
    }

因此,每次按下按钮时,种子值都设置为相同的值(除非文本框文本已更改,即)。这导致Random一遍又一遍地生成相同的数字。

您可以添加一个设置种子值的按钮,而不是在生成名称按钮中设置种子值,或者如果要保留单个按钮,则缓存当前种子值,并仅在更改时创建新的Random。像这样:

class NamesGenerator
{
    Random randomNumber;
    int currentSeed = -1;

    public void SetSeedValue(int seedValue)
    {
        if (currentSeed == seedValue)
            return;
        currentSeed = seedValue;
        randomNumber = new Random(seedValue);
    }
}

或者缓存TextBox的文本,这样您就不必在按下每个按钮时解析它。