防止在字典 c# 中作为值添加的对象的重复变量

Prevent duplicate variables of the objects added as Values in a dictionary c#

我的 Individual class 中有一个 Dictionary<int,int>

 public class Individual
    {
       Dictionary<int,int> pattern = new Dictionary<int,int>();
    }

我想在我的 population 词典中添加 <int,Individual> 对:

Dictionary<int,Individual> population = new Dictionary<int, Individual>();

当且仅当字典中没有其他 Individual 具有类似的 pattern 变量。

我目前的方法是天真地迭代 population 中已经存在的每个 Individual 的每个 pattern,但我相信使用不同的方法可以更快地完成此操作。

public bool same_dict(Dictionary<int, int> p1, Dictionary<int, int> p2)
//Meant to compare patterns
{
    if (p1.Count != p1.Count) return false;
    foreach (var feature in p1)
    {
        if (p2.ContainsKey(feature.Key))
        {
            if (feature.Value != p2[feature.Key]) return false;
        }
        else return false;
    }
    return true;
}

public bool matched is_duplicated(Individual ind, Dictionary<int, Individual> pop)
{
//Meant to compare Individuals
    foreach (var ind2 in pop)
    {
        if (same_dict(ind.pattern, ind2.Value.pattern))
        {
            return true;
        }
    }
    return false;
} 

我必须使用 ints 作为 population 字典的键,因为我用它来 link Individual 对象和程序的其他部分。 pattern 字典可以包含任意数量的 key:value 对,这就是我验证它们的 .Count 属性 是否相同的原因。

我不确定我是否正确理解了您的问题,但是...

If and only if there is no other Individual in the dictionary with a similar pattern variable

“相似模式变量”的意思是,正如我所想,两个 IndividualPattern 字典,其中包含相同的键和值(不知道,如何它可以存储很多“模式”。

所以我尝试使用 LINQ 的 .Any() 扩展方法来检查 population 字典中任何 IndividualPattern 字典是否具有与添加的相同的键和值 Individual。听起来很复杂,所以这里是代码示例(控制台):

public class Individual
{
    public Dictionary<int, int> Pattern { get; set; } = new Dictionary<int, int>();
}

static void Main()
{
    var population = new Dictionary<int, Individual>();
    var key = 0;

    for (; key < 5; key++) // Fill population with some Individuals
    {
        var individual = new Individual();
        individual.Pattern.Add(key + 1, key + 2);

        population.Add(key, individual);
    }

    // Print current population:
    Console.WriteLine("Population Dictionary:");
    foreach (var kvp in population)
        Console.WriteLine(kvp.Key + ": " +
                          string.Join(" | ", kvp.Value.Pattern.Select(pattern => pattern.Key + "," + pattern.Value)));

    // Creating new Individuals, which we will try to add to population
    var newIndividual1 = new Individual();
    newIndividual1.Pattern.Add(5, 6);
    var newIndividual2 = new Individual();
    newIndividual2.Pattern.Add(5, 5);
    var newIndividual3 = new Individual();
    newIndividual3.Pattern.Add(8, 9);

    Console.WriteLine();
    Console.WriteLine("Adding new Individuals:");

    if (AddIndividual(population, key, newIndividual1))
        key++;

    if (AddIndividual(population, key, newIndividual2))
        key++;

    if (AddIndividual(population, key, newIndividual3))
        key++;

    Console.ReadKey();
}

static bool AddIndividual(Dictionary<int, Individual> population, int newKey, Individual newIndividual)
{
    // Compare each Individual in population with newIndividual
    if (!population.Any(p => newIndividual.Pattern.Keys.Any(k => p.Value.Pattern.ContainsKey(k)) &&
                             newIndividual.Pattern.Values.Any(v => p.Value.Pattern.ContainsValue(v))))
    {
        population.Add(newKey, newIndividual);
        Console.WriteLine("Individual with pattern " +
                          string.Join(" | ", newIndividual.Pattern.Select(pattern => pattern.Key + "," + pattern.Value)) +
                          " successfully added to Population Dictionary.");

        return true;
    }
    else
    {
        Console.WriteLine("Individual with pattern " +
                          string.Join(" | ", newIndividual.Pattern.Select(pattern => pattern.Key + "," + pattern.Value)) +
                          " already exists in Population Dictionary.");

        return false;
    }
}

输出样本:

编辑。

您可以用 .SequenceEqual:

代替 .Any 方法比较键和值
if (!population.Any(p => p.Value.Pattern.OrderBy(kvp => kvp.Key).SequenceEqual(newIndividual.Pattern.OrderBy(kvp => kvp.Key))))
{
    population.Add(newKey, newIndividual);
}