C#将数字插入到排序位置的列表框中

Posted

技术标签:

【中文标题】C#将数字插入到排序位置的列表框中【英文标题】:C# inserting numbers into a list box in sorted position 【发布时间】:2019-04-13 00:22:58 【问题描述】:

请原谅我第一次发帖。我遇到了大学作业的问题。分配是一个“数字列表管理器”,基本上用户选择一个单选按钮(已排序或未排序),当他们单击按钮时,30 个数字将添加到尊重用户选择的列表框中。我对未排序的代码没有任何问题。讲师特别希望我们将排序后的数字添加到列表中并在添加时对其进行排序,而不是生成整个列表然后对其进行排序。

if (radUnsorted.Checked == true)//if unsorted

    RunChecks();
    do
    
        numberToInput = (rnd.Next(0, 100));//sets number to input to random number
        int i = 1;

        while (i < lstNumbers.Items.Count)//loops though whole list
        
            if (numberToInput == ConvertToInt32(lstNumbers.Items[i]))//checks that number doesnt already exist in list
            
                numberToInput = (rnd.Next(0, 101));//genrate new random number
                i = 0;//set to 0 to restart checking through the list
            
            else//if the number isnt at i index
            
                i++;//move onto next number
            
        

        lstNumbers.Items.Insert(i - 1, numberToInput);//insert the number
        RunChecks();//check if the list is full

     while (spaceLeft == true);//keep looping untill list is full

这是我将数字添加到未排序位置的列表的代码。我试过在网上查找,但我能看到的唯一方法是一个 for 循环将数字添加到列表中,然后另一个 for 循环对它们进行排序。

这是标准的 sn-p: 您必须在插入和删除期间使用您自己的代码操作列表,并且不得使用自动执行任务的 C# 方法,例如插入未排序列表仅需要将新值放置在当前最后一个条目之后的下一个可用位置,而插入排序列表需要您的代码定位插入点并移动任何更高值的条目以打开/释放插入包含新值的点。

我不要求任何人为我做这项工作,但即使是伪代码也会非常感激

【问题讨论】:

如果您想将项目添加到排序列表中,那么List.BinarySearch 是首选工具。请务必仔细阅读文档 - 它是一种有趣的野兽,但是一旦您掌握了它,您就可以确切地知道将新项目插入List 的位置。 实际上还有另一部分任务是使用搜索算法实现二进制和线性搜索,而不是自动功能您必须实现自己的线性搜索、二进制搜索、排序、插入和删除算法。 “除非必要,否则您不得使用自动提供此类功能的组件属性,包括 .add、.Contains、.IndexOf、.Insert、.Remove、.RemoveAt 和 .Sort。您可以使用 .Clear。您只能使用.Remove 或 .RemoveAt 删除列表框项目中的最后一个条目时。" 对不起,如果我误解了你,但你已经写了要做什么;):whilst inserting into a sorted list requires your code to locate the insertion point and move any higher value entries to open/free up the insertion point for the inclusion of the new value. 所以这样做:一旦你得到新的随机数,遍历列表 (for(.....)) 和检查数字是大于还是小于新数字。然后检查下一个(如果更小),或者将其保存在原处并将原始的向上移动(如果更大)。 顺便说一句,当您一件事上遇到困难时,请寻求家庭作业的帮助是完全可以的,只要您不要求我们做整件事。 【参考方案1】:

好的,首先我不确定这些检查列表是否已满是什么意思,你不能每次按下按钮时清除项目并遍历 1 到 30 吗?

无论如何,这是我为已排序和未排序的一些代码:

private void unsorted_Click(object sender, EventArgs e)

    lstNumbers.Items.Clear(); //clear any existing numbers, and add a new 30.
    var rand = new Random();
    for (var i = 0; i < 30; i++)
    
        var randNumber = rand.Next(0, 100);
        while (lstNumbers.Items.Contains(randNumber))
        
            //generate new number until it's unique to the list.
            randNumber = rand.Next(0, 100);
        
        lstNumbers.Items.Add(randNumber);
    


private void sorted_Click(object sender, EventArgs e)

    lstNumbers.Items.Clear(); //clear any existing numbers, and add a new 30.
    var rand = new Random();
    for (var i = 0; i < 30; i++)
    
        var randNumber = rand.Next(0, 100);
        while (lstNumbers.Items.Contains(randNumber))
        
            //generate new number until it's unique to the list.
            randNumber = rand.Next(0, 100);
        

        if (lstNumbers.Items.Count == 0)
        
            //we have no items, obviously the default position would be 0.
            lstNumbers.Items.Add(randNumber);
            continue; //next iteration
        

        //find out the sorted position
        var bestPos = 0;
        for (var j = 0; j < lstNumbers.Items.Count; j++) //loop through the current list.
        
            var currValue = Convert.ToInt32(lstNumbers.Items[j]);
            if (randNumber > currValue)
            
                bestPos = j + 1;
            
            else
            
                bestPos = j;
                break; //we no longer need to check, it will never be any less than this.
            
        
        if (bestPos < 0)
            bestPos = 0;
        lstNumbers.Items.Insert(bestPos, randNumber);
    

【讨论】:

对不起,我应该解释一下空格。其他标准之一是允许用户手动插入自己的号码,然后您可以使用生成按钮填充列表中的剩余空间。有一个相当广泛的标准列表和我们可以做和不能做的事情,例如我们不能在除最后一个索引之外的特定索引处删除,因此我们选择删除的任何数字都需要移动到列表的末尾然后删除。这非常有帮助,我想我知道如何将其应用到我的作业中。【参考方案2】:

您已经在遍历列表并读取每个值,因此您需要做的就是检查现有值是否大于您插入的值。如果是这样,您应该在刚刚检查的项目之前插入它。

            var inserted = false;
            while (i < lstNumbers.Items.Count)//loops though whole list
            
                if (numberToInput == Convert.ToInt32(lstNumbers.Items[i]))//checks that number doesnt already exist in list
                
                    numberToInput = (rnd.Next(0, 101));//genrate new random number
                    i = 0;//set to 0 to restart checking through the list
                
                else if (numberToInput < Convert.ToInt32(lstNumbers.Items[i])
                
                    lstNumbers.Items.Insert(i - 1, numberToInput);//insert the number
                    inserted = true;
                 
                else//if the number isnt at i index
                
                    i++;//move onto next number
                
            

            if (!inserted)
             
                lstNumbers.Items.Insert(i - 1, numberToInput);//insert the number
            

注意检查新项目何时需要放在列表末尾。

我想这就是你的老师想要的,理解如何使用数组很重要,但实际上在 C# 中对列表进行排序的最佳方法不是使用数组,而是使用 List 或其他拥有它自己的类排序方法。

        var myList = new List<int>();
        myList.Add(5);
        myList.Add(3);
        myList.Add(1);

        myList.Sort();

如果您有一百万个项目,这将更快、更高效,并且它适用于字符串或日期等。

List 也有一个Contains 方法,以及其他几个让生活更轻松的快捷方式。 @ThePerplexedOne 是正确的,这是在填充列表后排序,您可以使用 SortedList,它会自动在正确的位置插入项目。

【讨论】:

他特别说讲师希望代码在生成数字时找到正确的排序位置,而不是之后。 在这种情况下使用 SortedList 或类似的东西会作弊。我很确定讲师希望他们编写自己的排序方法。我在下面给出了一个例子。【参考方案3】:

我使用SortedList 提出了可能更简单的方法来解决这个问题。

SortedList<int, object> sortedList = new SortedList<int, object>();

sortedList.Add(4, null);
sortedList.Add(1, null);
sortedList.Add(7, null);

foreach(KeyValuePair<int, object> k in sortedList)

    Console.WriteLine(k.Key);

【讨论】:

分配的标准之一是我不能使用内置方法进行排序。不幸的是,我需要手动编码所有排序

以上是关于C#将数字插入到排序位置的列表框中的主要内容,如果未能解决你的问题,请参考以下文章

如何将文本框文本拆分为列表框 C#

对列表框中的项目列表进行排序

识别不同文本区域中的光标位置并在列表框中选择项目时插入文本

如何在检查唯一值的同时将数据从一个表单插入到另一个表单的列表框中?

C#匿名委托实现递归,将所有部门根据上下级关系显示在一个列表中,用于展示到下拉框中

在富文本框中定位列表框