泛型节点声明

发布于 2024-12-12 09:03:19 字数 3977 浏览 0 评论 0原文

Microsoft 将此作为学习泛型的冒泡排序示例。直到第 76 行和第 77 行才有意义。这些声明怎么可能呢?节点是一个类。不需要用new实例化吗? 您将如何优化排序?哪一部分是通用的,哪一部分是非通用的?

1   public class GenericList<T> : System.Collections.Generic.IEnumerable<T>
2       {
3           protected Node head;
4           protected Node current = null;
5   
6           // Nested class is also generic on T
7           protected class Node
8           {
9               public Node next;
10              private T data;  //T as private member datatype
11   
12              public Node(T t)  //T used in non-generic constructor
13              {
14                  next = null;
15                  data = t;
16              }
17  
18              public Node Next
19              {
20                  get { return next; }
21                  set { next = value; }
22              }
23  
24              public T Data  //T as return type of property
25              {
26                  get { return data; }
27                  set { data = value; }
28              }
29          }
30  
31          public GenericList()  //constructor
32          {
33              head = null;
34          }
35  
36          public void AddHead(T t)  //T as method parameter type
37          {
38              Node n = new Node(t);
39              n.Next = head;
40              head = n;
41          }
42  
43          // Implementation of the iterator
44          public System.Collections.Generic.IEnumerator<T> GetEnumerator()
45          {
46              Node current = head;
47              while (current != null)
48              {
49                  yield return current.Data;
50                  current = current.Next;
51                  
52              }
53          }
54  
55          System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
56          {
57              return GetEnumerator();
58          }
59      }
60  
61      public class SortedList<T> : GenericList<T> where T : System.IComparable<T>
62      {
63          // A simple, unoptimized sort algorithm that 
64          // orders list elements from lowest to highest:
65  
66          public void BubbleSort()
67          {
68              if (null == head || null == head.Next)
69              {
70                  return;
71              }
72              bool swapped;
73  
74              do
75              {
76                  Node previous = null;
77                  Node current = head;
78  
79                  
80                  //Console.WriteLine(previous.GetType());
81                  //Console.ReadLine();
82  
83                  swapped = false;
84                  
85                   
86                  //Debug.WriteLine(p);
87                  //Debug.WriteLine("Testing " + current.ToString());
88  
89                  while (current.next != null)
90                  {
91                      //  Because we need to call this method, the SortedList
92                      //  class is constrained on IEnumerable<T>
93                      if (current.Data.CompareTo(current.next.Data) > 0)
94                      {
95                          Node tmp = current.next;
96                          current.next = current.next.next;
97                          tmp.next = current;
98  
99                          if (previous == null)
100                         {
101                             head = tmp;
102                         }
103                         else
104                         {
105                             previous.next = tmp;
106                         }
107                         previous = tmp;
108                         swapped = true;
109                     }
110                     else
111                     {
112                         previous = current;
113                         current = current.next;
114                     }
115                 }
116             } while (swapped);
117         }
118     }

Microsoft gives this as an Bubble sort example for learning generics. It makes sense until I get to lines 76 and 77. How are those declarations possible? Node is a class. Don't you have to instantiate it with new?
How would you optimize the sort? Which is part is generic and which is non-generic?

1   public class GenericList<T> : System.Collections.Generic.IEnumerable<T>
2       {
3           protected Node head;
4           protected Node current = null;
5   
6           // Nested class is also generic on T
7           protected class Node
8           {
9               public Node next;
10              private T data;  //T as private member datatype
11   
12              public Node(T t)  //T used in non-generic constructor
13              {
14                  next = null;
15                  data = t;
16              }
17  
18              public Node Next
19              {
20                  get { return next; }
21                  set { next = value; }
22              }
23  
24              public T Data  //T as return type of property
25              {
26                  get { return data; }
27                  set { data = value; }
28              }
29          }
30  
31          public GenericList()  //constructor
32          {
33              head = null;
34          }
35  
36          public void AddHead(T t)  //T as method parameter type
37          {
38              Node n = new Node(t);
39              n.Next = head;
40              head = n;
41          }
42  
43          // Implementation of the iterator
44          public System.Collections.Generic.IEnumerator<T> GetEnumerator()
45          {
46              Node current = head;
47              while (current != null)
48              {
49                  yield return current.Data;
50                  current = current.Next;
51                  
52              }
53          }
54  
55          System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
56          {
57              return GetEnumerator();
58          }
59      }
60  
61      public class SortedList<T> : GenericList<T> where T : System.IComparable<T>
62      {
63          // A simple, unoptimized sort algorithm that 
64          // orders list elements from lowest to highest:
65  
66          public void BubbleSort()
67          {
68              if (null == head || null == head.Next)
69              {
70                  return;
71              }
72              bool swapped;
73  
74              do
75              {
76                  Node previous = null;
77                  Node current = head;
78  
79                  
80                  //Console.WriteLine(previous.GetType());
81                  //Console.ReadLine();
82  
83                  swapped = false;
84                  
85                   
86                  //Debug.WriteLine(p);
87                  //Debug.WriteLine("Testing " + current.ToString());
88  
89                  while (current.next != null)
90                  {
91                      //  Because we need to call this method, the SortedList
92                      //  class is constrained on IEnumerable<T>
93                      if (current.Data.CompareTo(current.next.Data) > 0)
94                      {
95                          Node tmp = current.next;
96                          current.next = current.next.next;
97                          tmp.next = current;
98  
99                          if (previous == null)
100                         {
101                             head = tmp;
102                         }
103                         else
104                         {
105                             previous.next = tmp;
106                         }
107                         previous = tmp;
108                         swapped = true;
109                     }
110                     else
111                     {
112                         previous = current;
113                         current = current.next;
114                     }
115                 }
116             } while (swapped);
117         }
118     }

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

英雄似剑 2024-12-19 09:03:19

C# 中的 class 类型可以使用 null 或与声明类型兼容的值进行初始化。第 76 行和第 77 行看起来像这样

Node previous = null;
Node current = head;

这里值 null 是合法的。它本质上是在说“我没有价值”。对 head 的赋值也是合法的,因为 head 也是 Node 类型。结果是两个引用 headcurrent 引用相同的 Node 对象值。通过其中一个引用修改 Node 实例将对另一个引用可见。

A class type in C# can be initialized with null or a value which is of a compatible type with the declaration. Lines 76 and 77 look like so

Node previous = null;
Node current = head;

Here the value null is legal. It essentially says "I have no value". The assignment to head is also legal because head is also of type Node. The result is the two references head and current refer to the same Node object value. Modifying the Node instance through one of the references will be visible to the other.

北音执念 2024-12-19 09:03:19

您将 previousnext 分别分配给 nullhead。这是一个赋值操作,就像其他操作一样。除非您实际创建对象的新实例,否则不需要使用 new。

通用部分是引用 T 的任何内容。它是实例化类时提供的泛型类型。一个很好的例子是 List,它创建 T 类型的对象列表。您可以将其实例化为 List(表示字符串列表)、List(表示整数列表)等。

You're assigning previous and next to null and head respectively. It's an assignment operation, just like any other. You don't need to use new unless you're actually creating a new instance of the object.

The generic parts are anything that refers to T. It's a generic type that is supplied when the class is instanciated. A good example is List<T>, which creates a list of objects of type T. You could instance this as List<string> for a list of strings, List<int> for a list of ints, etc.

轻许诺言 2024-12-19 09:03:19

这些引用可能指向实例,也可能只是null

您可以将引用分配给其他引用:

Foo f1 = new Foo();
Foo f2 = f1;
Foo f3 = null;

These are references that could be pointing to instances of a class or can be just null.

You can assign references to other references:

Foo f1 = new Foo();
Foo f2 = f1;
Foo f3 = null;
感悟人生的甜 2024-12-19 09:03:19

该代码中的第 76 行和第 77 行没有实例化任何对象。正如您所说,Node 是一个类。 .NET 中的类始终是引用类型,这意味着:

  1. 引用类型变量的值是对对象的引用(或什么都不是)。
  2. 引用类型的变量可以被赋予值null,这意味着该变量不引用任何内容。
  3. 将一个引用类型的变量分配给另一个引用类型的变量会复制引用,而不是对象。

No objects are being instantiated on lines 76 and 77 in that code. As you said, Node is a class. Classes in .NET are always reference types which means that:

  1. The value of a variable of a reference type is a reference to an object (or nothing).
  2. Variables of a reference type can be assigned the value null, which means that the variable references nothing.
  3. Assigning one variable of a reference type to another variable of a reference type copies the reference, not the object.
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文