c#需要帮助才能理解这段代码

时间:2014-04-15 17:44:04

标签: c# zip intersect

我目前正在开发一个项目,这是一个在Windows窗体中创建的Mastermind游戏。

每次玩家猜测他认为可能是正确的颜色顺序的地方之后,他就会知道他的针脚在正确的位置有多少是正确的颜色,而正确的颜色却在错误的地方。

我问了一位对编程有更多经验的伙伴,他给了我一些帮助:

/* RightCRightP is the variable for how many pins which are right colour and on right
                place. 
   RightCWrongP is the variable for how many pins which are right colour but on wrong
                place.
   guessList    is a list including the players guesses.
   answerList   is a list including the right answer ( right order ).
*/
//His code
var RightCRightP = guessList
        .Zip(answerList, (g, s) => g == s)
        .Count(z => z);

var RightCWrongP = guessList
        .Intersect(answerList)
        .Sum(c =>
            System.Math.Min(
                answerList.Count(x => x == c),
                guessList.Count(x => x == c))) - RightCRightP;

问题是,我想了解这段代码中的每件事情。可悲的是,我不能亲自问他,因为他目前正在度假。

2 个答案:

答案 0 :(得分:4)

我们将使用的数据将是

guesses = [1,2,0,3]
answers = [1,2,3,4]

第一次表达

guessList.Zip(answerList, (g, s) => g == s)

Zip扩展通过对guessList和answerList之间的每个对应元素执行提供的lambda操作来“拉链”两个列表,并返回结果的集合。

Zip essentialy yield

 [f(guesses[0], answers[0]), f(guesses[1],
 answers[1]), f(guesses[2], answers[2]), f(guesses[3],answers[3])] 

其中函数f是 lambda函数提供:

f(g,s) => g == s

结果是[true,true,false,false]

我们接着

.Count(z => z) 

的Zip方法的结果,它计算zipresult中的元素数量是否为真。

(如果有帮助,请将其读作.Count(z => z!= false))

因此,Count是2因为我们有两个是真的元素。 所以我们的RightCRightP是2.检查我们的输入这是我们的预期,因为我们的前两个猜测是正确的颜色和位置,但最后两个不是。

第二次表达

guessList.Intersect(answerList) 

引用http://www.dotnetperls.com/intersect Intersect应用集合论。在集合论中,交集是两个集合中找到的每个集合的子集。 简而言之,它产生了两个列表中存在的一组项目。请记住,set元素是不同的。

因此,根据我们的上述猜测和答案,[1,2,0,3]和[1,2,3,4]的交点将产生[1,2,3](注意这里包括3但是它的不是在正确的地方!)

然后我们应用相交结果的Sum运算。 Sum将遍历每个元素并找到由提供的lambda表达式产生的结果的总和。 这个交叉操作的目的是为我们提供一个正确猜测的颜色列表,无论正确的位置如何。

我们的lambda是

c => Min(answerList.Count(x => x == c), guessList.Count(x => x == c))

我们计算answerList和guessList中等于颜色c的值的数量,并取两者中较小的一个。 此总和操作为我们提供正确猜测颜色的项目数,而不管正确放置。 因此,迭代[1,2,3]的交点结果,lambda将为所有迭代返回值1,因此Sum将为1 + 1 + 1 = 3.这是我们正确猜测颜色的计数。

由于我们现在有正确颜色数,我们可以通过用右减去正确颜色的数量来推断正确颜色与错误放置的数量刊登位置

RightCWrongP = 3 - 2 => 1.

检查我们的输入猜测= [1,2,0,3]和答案= [1,2,3,4]

RightColorWrongP是我们预期的1,因为我们对colorvalue 3的猜测是正确的颜色但不在正确的位置。

P.S。如果我说的是错的,请在评论中告诉我,不要只是downvote,我不是LINQ或C#向导。

答案 1 :(得分:2)

你看到的是Linq代码。我现在将解释第一行,让你自己尝试理解第二行。

var RightCRightP = guessList
        .Zip(answerList, (g, s) => g == s)
        .Count(z => z);

这一行基本上取两个列表(guesslist和answerlist)并比较每个答案(g == s)并计算相同的答案。

例如,如果guessList是{1,2,3,4,5}并且答案列表是{1,2,4,5,3}那么" RightCRightP"将是2.(1 == 1,2 == 2但3!= 4,4!= 5,3!= 5)

添加我的完整性答案:

以下代码:

    List<int> guessList = new List<int>() { 1, 2, 3, 4, 5 };
    List<int> answerList = new List<int>() { 1, 2, 4, 5, 3 };

    List<bool> zipList = guessList.Zip(answerList, (g, s) => g == s).ToList<bool>();

    Console.WriteLine("Content of 'zipList': ");
    foreach (bool b in zipList) { Console.WriteLine(b); }

    int RightCRightP = zipList.Count(z => z);

    Console.WriteLine("Number of matches in 'RightCRightP': " + RightCRightP);

输出:

Content of 'zipList':
True
True
False
False
False
Number of matches in 'RightCRightP': 2