有两个列表:
List<int> list2 = new List<int>(new[] { 1, 2, 3, 5, 6 }); // missing: 0 and 4
List<int> list1 = new List<int>(new[] { 0, 1, 2, 3, 4, 5, 6 });
如何比较两个列表,在List1中找到缺少的数字并从List1中删除这些数字?更确切地说,我需要找到一种方法来指定开始和结束位置以进行比较。
我认为过程应该与此非常相似:
第1步。
int start_num = 3; // we know that comparisons starts at number 3
int start = list2.IndexOf(start_num); // we get index of Number (3)
int end = start + 2; // get ending position
int end_num = list2[end]; // get ending number (6)
现在我们在List2(3,5,6)
中有数字位置(和数字本身)进行比较第2步。要获取List1中的数字位置进行比较,我们可以执行以下操作:
int startlist1 = list1.IndexOf(start_num); // starting position
int endlist1 = list1.IndexOf(end_num); // ending position
范围如下:(3,4,5,6)
第3步。比较。棘手的部分从这里开始,我需要帮助
基本上我们现在需要比较(3,5,6)的list2和(3,4,5,6)的list1。缺少的数字是“4”。
// I have troubles with this step but the result will be:
int remove_it = 4; // or int []
步骤4.奇数删除。
int remove_it = 4;
list1 = list1.Where(a => a != remove_it).ToList();
效果很好,但是如果我们有2个缺失数字会怎么样?即。
int remove_it = 4 // becomes int[] remove_it = {4, 0}
结果正如您所猜测的那样,结果是新的List1,其中没有数字4。
richTextBox1.Text = "" + string.Join(",", list1.ToArray()); // output: 0,1,2,3,5,6
textBox1.Text = "" + start + " " + start_num; // output: 2 3
textBox3.Text = "" + end + " " + end_num; // output: 4 6
textBox2.Text = "" + startlist1; // output: 3
textBox4.Text = "" + endlist1; // output: 6
你能帮我解决第3步或指出正确的方向吗?
另外,你能说如果起始号码(start_num)是最后一个号码会发生什么,但我需要接下来的两个号码?在上面的例子中,数字 3,5,6,但它们应该与 5,6,0 或 6,0,1 或 0,1,2 。
答案 0 :(得分:3)
回答第一部分:
var list3 = list1.Intersect(list2);
这会将list3
设置为{ 0, 1, 2, 3, 4, 5, 6 } - { 0, 4 } = { 1, 2, 3, 5, 6 }
对第1步的反应:
int start_num = 3; //我们知道比较从3号开始 int start = list2.IndexOf(start_num); //我们得到Number(3)的索引
int end = start + 2; //获得结束位置
你从哪里获得所有这些神奇的数字(3,+ 2)?
我觉得你过分思考这个问题了。
答案 1 :(得分:1)
var result = list1.Intersect(list2)
如果您确实需要将结果作为列表,则可以在末尾添加.ToList
。
答案 2 :(得分:1)
List<int> list2 = new List<int>(new[] { 1, 2, 3, 5, 6 }); // missing: 0 and 4
List<int> list1 = new List<int>(new[] { 0, 1, 2, 3, 4, 5, 6 });
// find items in list 2 notin 1
var exceptions = list1.Except(list2);
// or are you really wanting to do a union? (unique numbers in both arrays)
var uniquenumberlist = list1.Union(list2);
// or are you wanting to find common numbers in both arrays
var commonnumberslist = list1.Intersect(list2);
答案 3 :(得分:0)
也许您应该使用OrderedList而不是List ...
答案 4 :(得分:0)
这样的事情:
list1.RemoveAll(l=> !list2.Contains(l));
答案 5 :(得分:0)
您可以将Intersect
与Skip
和Take
结合使用,以获得与范围相结合的交叉点逻辑(这里我们忽略了因为我们跳过它而忽略了事实0):< / p>
static void Main(string[] args)
{
var list1 = new List<int> { 1, 2, 3, 4, 5 };
var list2 = new List<int> { 0, 1, 2, 3, 5, 6 };
foreach (var i in list2.Skip(3).Take(3).Intersect(list1))
Console.WriteLine(i); // Outputs 3 then 5.
Console.Read();
}
虽然如果我真的真的诚实,我不确定会被问到什么 - 我唯一肯定的是交叉部分:
var list1 = new List<int> { 1, 2, 3, 4, 5 };
var list2 = new List<int> { 0, 1, 2, 3, 5, 6 };
foreach (var i in list2.Intersect(list1))
Console.WriteLine(i); // Outputs 1, 2, 3, 5.
答案 6 :(得分:0)
要获取list1
中但不在list2
中的数字,请使用Except
扩展名方法:
IEnumerable<int> missing = list1.Except(list2);
要循环显示此结果以将其从list1
中删除,您必须实现结果,否则它会在您更改时从列表中读取,并且您将获得例外:
List<int> missing = list1.Except(list2).ToList();
现在你可以删除它们:
foreach (int number in missing) {
list1.Remove(number);
}
答案 7 :(得分:0)
我不确定我理解你的问题,我希望我给你的解决方案对你有好处。
您有2个列表:
列表list2 =新列表(new [] {1,2,3,5,6}); //缺少:0和4 列表list1 =新列表(new [] {0,1,2,3,4,5,6});
要从list1中删除list2中所有缺少的数字,我建议使用此解决方案: 建立一个缺少数字的新列表:
列出diff = new List();
然后在此列表中输入您需要删除的所有数字。现在删除过程应该很简单,只需要在diff中添加所有元素并从list2中删除。
答案 8 :(得分:0)
我是否正确理解该算法是: 1)取List 2中的第一个数字并在List1中找到这样的数字, 2)然后删除列表1中的所有内容,直到找到第二个数字表单list2(5) 3)对list2中的下一个数字重复步骤2)。?
答案 9 :(得分:0)
List<int> list2 = new List<int>() { 1, 2, 3, 5, 6 }; // missing: 0 and 4
List<int> list1 = new List<int>() { 0, 1, 2, 3, 4, 5, 6 };
int number = 3; // starting position
int indexer = list2.BinarySearch(number);
if (indexer < 0)
{
list2.Insert(~index, number); // don't look at this part
}
// get indexes of "starting position"
int index1 = list1.Select((item, i) => new { Item = item, Index = i }).First(x => x.Item == number).Index;
int index2 = list2.Select((item, i) => new { Item = item, Index = i }).First(x => x.Item == number).Index;
// reorder lists starting at "starting position"
List<int> reorderedList1 = list1.Skip(index1).Concat(list1.Take(index1)).ToList(); //main big
List<int> reorderedList2 = list2.Skip(index2).Concat(list2.Take(index2)).ToList(); // main small
int end = 2; // get ending position: 2 numbers to the right
int end_num = reorderedList2[end]; // get ending number
int endlist1 = reorderedList1.IndexOf(end_num); // ending position
//get lists for comparison
reorderedList2 = reorderedList2.Take(end + 1).ToList();
reorderedList1 = reorderedList1.Take(endlist1 + 1).ToList();
//compare lists
var list3 = reorderedList1.Except(reorderedList2).ToList();
if (list3.Count != 0)
{
foreach (int item in list3)
{
list1 = list1.Where(x => x != item).ToList(); // remove from list
}
}
// list1 is the result that I wanted to see
如果有任何方法可以优化此代码,请通知我。欢呼声。