字符串C#的排序问题

时间:2017-02-27 17:50:03

标签: c# arrays sorting bucket-sort

我正在编写一个程序,其中包含学生信息的数据,其中包含学生ID#字段,学生名字字段和学生姓名字段。用户将输入每个学生(最多20名学生)的数据,或者直到用户输入“999”作为学生ID字段。接下来,我想根据姓氏字段将学生信息分成两个独立的桶。

我遇到了正确分离存储桶的问题。我将使用CompareTo方法比较学生姓氏数组的姓氏字符串,但是当我打印存储桶时,它们会混淆。例如,以A-K开头的姓氏应该进入“低值”桶,而以J-Z开头的姓氏应该进入“高值”桶。

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.Threading.Tasks;

    namespace _123_Assignment2
    {
    using System;
    using static System.Console;
    class Program
    {
    struct student
    {
        public int studentId;
        public string firstName;
        public string lastName;
    };

    static void Main(string[] args)
    {
        student[] studentInfo = new student[20];
        string[] bucketLow = new string[20];
        string[] bucketHigh = new string [20];
        int x = 0;
        int y = 0;
        int z = 1;



        WriteLine("Enter student ID number:");
        studentInfo[x].studentId = Convert.ToInt32(ReadLine());

        while (studentInfo[x].studentId != 999)
        {
            WriteLine("Enter first name:");
            studentInfo[x].firstName = ReadLine();
            WriteLine("Enter last name:");
            studentInfo[x].lastName = ReadLine();
            x++;
            WriteLine("Enter student ID number:");
            studentInfo[x].studentId = Convert.ToInt32(ReadLine());
        }


        for (int j = 0; j < x; j++)
        {

      if(studentInfo[j].lastName.CompareTo(studentInfo[z].lastName)<= 0)

                bucketLow[y] = studentInfo[j].lastName;
            else
                bucketHigh[y] = studentInfo[j].lastName;

                y++;
                z++;
        }

        WriteLine("Unsorted Table:");
        for (int j = 0; j < studentInfo.Length; j++)
        {

       WriteLine("{0}{1}{2}",studentInfo[j].studentId,studentInfo[j].firstName,
       studentInfo[j].lastName);
        }
        WriteLine("Bucket 1:");
        for (int j = 0; j < x; j++)
        {
            WriteLine(bucketLow[j]);
        }
        WriteLine("Bucket 2:");
       for (int j = 0; j < x; j++)
        {
            WriteLine(bucketHigh[j]);
       }
    }
}

}

我相信我没有正确编写CompareTo方法,我尝试分别从数组的开头和结尾进行排序并继续得到相同的结果?

3 个答案:

答案 0 :(得分:1)

由于这似乎是家庭作业,我将不会为您实际编写正确的代码。但这至少是你的一些问题:

  1. 直接解决您的问题,您必须对数组元素进行排序的代码使用错误的比较。如果您有两个存储桶,并且您希望一个表示以AK开头的姓氏,另一个表示以LZ开头的姓氏,那么您需要与KL进行比较才能确定正确的存储桶。与其他名称相比,只是随机化数据。像string.Compare(studentInfo[j].lastName, "L", StringComparison.CurrentCultureIgnoreCase) < 0这样的东西应该有效。
  2. 您需要维护两个索引,每个索引一个,如果您实际上已将学生记录复制到该存储桶,则只增加该存储桶的索引。
  3. 如果你真的尝试为20名学生输入数据,那么你当前的代码会因IndexOutOfRangeException而崩溃,因为你增加x并将ID值存储到数组中,而不检查你是否&#39已经输入了20名学生的数据。输入20名学生后,即使用户输入999while条件也不会检查,直到为时已晚并且代码已尝试存储值进入数组。
  4. 可能还有其他问题;那些是我乍一看的那些。

    为了将来参考,您应该确保在Stack Overflow上提出问题时提供了一个好的Minimal, Complete, and Verifiable code example。你走近了;至少代码是完整的。但是,不要让其他SO用户输入您的测试数据。编写一个单独的程序,其中包含内置的所有数据,没有用户提示,并且没有任何,这些并非严格要求重现您的问题& #39;有了。

答案 1 :(得分:0)

我不认为你的排序是有效的(j和z比较):

studentInfo[j].lastName.CompareTo(studentInfo[z].lastName)<= 0

尝试简化您的铲斗排序 - 如果您知道您的铲斗是A-K和J-Z,您可能应该替换以下部分:

for (int j = 0; j < x; j++)
{
  if(studentInfo[j].lastName.CompareTo(studentInfo[z].lastName)<= 0)
      bucketLow[y] = studentInfo[j].lastName;
   else
      bucketHigh[y] = studentInfo[j].lastName;
      y++;
      z++;
   }
}

尝试类似:

for (var i = 0; i < studentInfo.Length; i++)
{
   if (studentInfo[i].lastName[0] <= 'K')
      bucketLow[y] = studentInfo[i].lastName;
   else
      bucketHigh[y] = studentInfo[i].lastName;

   y++;
}

(当然,添加一些检查,你有一个至少有1个字符的有效输入,等等......)

答案 2 :(得分:0)

如果必须使用结构和数组,那么您可以考虑使用以下代码将名称分隔到适当的存储区中。正如我评论的那样,您需要两个索引,每个索引一个。因为您要将数组大小修复为20,所以如果小于20,则在输出结果时会有空行。

x = studentInfo.Length;
int lowIndex = 0;
int highIndex = 0;

for (int j = 0; j < x; j++) {
  if (String.CompareOrdinal(studentInfo[j].lastName, "L") < 0) {
    bucketLow[lowIndex] = studentInfo[j].lastName;
    lowIndex++;
  } else {
    bucketHigh[highIndex] = studentInfo[j].lastName;
    highIndex++;
  }
}