• 算法Sedgewick第四版-第1章基础-016一list


      1 import java.util.Iterator;
      2 import java.util.NoSuchElementException;
      3 
      4 public class List<Item> implements Iterable<Item>
      5 {
      6     private int N;
      7     private Node first;
      8     private Node last;
      9 
     10     private class Node
     11     {
     12         private Item item;
     13         private Node next;
     14     }
     15 
     16     public List()
     17     {
     18         first = null;
     19         last  = null;
     20     }
     21     
     22     public List(Item[] a)
     23     {
     24         for (Item t : a)
     25             append(t);
     26     }
     27 
     28     public List(Iterable<Item> coll)
     29     {
     30         for (Item t : coll)
     31             append(t);
     32     }
     33 
     34     public boolean isEmpty()
     35     {
     36         return first == null;
     37     }
     38 
     39     public int size()
     40     {
     41         return N;     
     42     }
     43     
     44     public Item first()
     45     {
     46         if (isEmpty()) throw new RuntimeException("List is empty");
     47         return first.item;
     48     }
     49     
     50     public Item last()
     51     {
     52         if (isEmpty()) throw new RuntimeException("List is empty");
     53         return last.item;
     54     }
     55     
     56     public Item removeFirst()
     57     {
     58         if (isEmpty()) throw new RuntimeException("List is empty");
     59         Item item = first.item;
     60         first = first.next;
     61         N--;
     62         if (isEmpty()) last = null;   // to avoid loitering
     63         return item;
     64     }
     65     
     66     public void prepend(Item item)
     67     {
     68         Node x = new Node();
     69         x.item = item;
     70         if (isEmpty()) { first = x;      last = x;  }
     71         else           { x.next = first; first = x; }
     72         N++;
     73     }
     74 
     75     public void append(Item item)
     76     {
     77         Node x = new Node();
     78         x.item = item;
     79         if (isEmpty()) { first = x;     last = x; }
     80         else           { last.next = x; last = x; }
     81         N++;
     82     }
     83     
     84     public String toString()
     85     {
     86         StringBuilder s = new StringBuilder();
     87         for (Item item : this)
     88             s.append(item + " ");
     89         return s.toString();
     90     } 
     91  
     92     public Iterator<Item> iterator()
     93     {
     94         return new ListIterator();  
     95     }
     96 
     97     private class ListIterator implements Iterator<Item>
     98     {
     99         private Node current = first;
    100 
    101         public boolean hasNext()  { return current != null;                     }
    102         public void remove()      { throw new UnsupportedOperationException();  }
    103 
    104         public Item next()
    105         {
    106             if (!hasNext()) throw new NoSuchElementException();
    107             Item item = current.item;
    108             current = current.next; 
    109             return item;
    110         }
    111     }
    112     
    113     /*****************
    114      * Exercise 1.3.19
    115      *****************/
    116     public Item removeLast()
    117     {
    118         if (isEmpty()) throw new RuntimeException("List is empty");
    119         if (first == last) return removeFirst();
    120         Item item = last.item;
    121         
    122         Node prev = null,
    123              curr = first;
    124         while (curr.next != null)
    125         {
    126             prev = curr;
    127             curr = curr.next;
    128         }
    129         prev.next = null;
    130         last = prev;
    131         N--;
    132         
    133         return item;
    134     }
    135     
    136     /*****************
    137      * Exercise 1.3.20
    138      *****************/
    139     public Item delete(int k)
    140     {
    141         if (k < 1) return null;
    142         
    143         int i = 1;
    144         Node prev = null,
    145              curr = first;
    146         
    147         while (i < k && curr != null)
    148         {
    149             prev = curr;
    150             curr = curr.next;
    151             i++;
    152         }
    153         
    154         if (curr != null)
    155         {
    156             if (prev == null)
    157                 first = curr.next;
    158             else
    159                 prev.next = curr.next;
    160             
    161             if (curr.next == null)
    162                 last = prev;
    163             
    164             N--;
    165             return curr.item;
    166         }
    167         else
    168             return null;
    169     }
    170     
    171     /*************************************
    172      * Exercise 1.3.21
    173      * (Renamed from find() to contains())
    174      *************************************/
    175     public boolean contains(Item item)
    176     {
    177         Node curr = first;
    178         while (curr != null && !curr.item.equals(item))
    179             curr = curr.next;
    180         return curr != null;
    181     }
    182     
    183     /*****************
    184      * Exercise 1.3.26
    185      *****************/
    186     public void remove(Item item)
    187     {
    188         List<Integer> idx = new List<Integer>();
    189         int i = 1;
    190         
    191         for (Item x : this)
    192         {
    193             if (x.equals(item))
    194                 idx.prepend(i);
    195             i++;
    196         }
    197         
    198         for (int k : idx)
    199             delete(k);
    200     }
    201     
    202     /***************************************
    203      * Recursive solution to Exercise 1.3.26
    204      ***************************************/
    205     public void removeRec(Item item)
    206     {
    207         first = remove_Node(first, item);
    208         setLastAndN();
    209     }
    210     
    211     private Node remove_Node(Node node, Item item)
    212     {
    213         if (node != null)
    214         {
    215             Node rest = remove_Node(node.next, item);
    216             
    217             if (node.item.equals(item))
    218                 return rest;
    219             else
    220             {
    221                 node.next = rest;
    222                 return node;
    223             }
    224         }
    225         else
    226             return null;
    227     }
    228     
    229     private void setLastAndN()
    230     {
    231         last = first;
    232         N = 0;
    233         if (first != null)
    234         {
    235             N++;
    236             while (last.next != null)
    237             {
    238                 last = last.next;
    239                 N++;
    240             }
    241         }
    242     }
    243     
    244     
    245     /*********************
    246      * Operations on nodes
    247      *********************/
    248     
    249     public Node node(int k)
    250     {
    251         if (k < 1) return null;
    252         
    253         int i = 1;
    254         Node curr = first;
    255         
    256         while (i < k && curr != null)
    257         {
    258             curr = curr.next;
    259             i++;
    260         }
    261         
    262         return curr;
    263     }
    264     
    265     public Node createNode(Item item)
    266     {
    267         Node node = new Node();
    268         node.item = item;
    269         return node;
    270     }
    271     
    272     /*****************
    273      * Exercise 1.3.24
    274      *****************/
    275     public void removeAfter(Node node)
    276     {
    277         if (node != null && node.next != null)
    278         {
    279             if (node.next.next == null)
    280                 last = node;
    281             node.next = node.next.next;
    282             N--;
    283         }
    284     }
    285     
    286     /*****************
    287      * Exercise 1.3.25
    288      *****************/
    289     public void insertAfter(Node a, Node b)
    290     {
    291         if (a != null && b != null)
    292         {
    293             if (last == a)
    294                 last = b;
    295             b.next = a.next;
    296             a.next = b;
    297             N++;
    298         }
    299     }
    300     
    301     /*************************************************
    302      * Exercise 1.3.27
    303      * Type 'Item' must implement interface Comparable
    304      *************************************************/
    305     public Item max(Node node)
    306     {
    307         if (node == null) throw new RuntimeException("List is empty");
    308         return max(node, null);
    309     }
    310     
    311     public Item max(Node node, Item def)
    312     {
    313         if (node == null)
    314             return def;
    315         
    316         Item max = node.item;
    317         Node curr = node;
    318         
    319         while (curr.next != null)
    320         {
    321             curr = curr.next;
    322             if (((Comparable)max).compareTo(curr.item) < 0)
    323                 max = curr.item;
    324         }
    325         
    326         return max;
    327     }
    328     
    329     /*************************************************
    330      * Exercise 1.3.28
    331      * (recursive variant of Exercise 1.3.27)
    332      * Type 'Item' must implement interface Comparable
    333      *************************************************/
    334     public Item maxRec(Node node, Item def)
    335     {
    336         if (node == null)
    337             return def;
    338         else
    339             return maxRec(node);
    340     }
    341     
    342     public Item maxRec(Node node)
    343     {
    344         if (node == null) throw new RuntimeException("List is empty");
    345         
    346         if (node.next == null)
    347             return node.item;
    348         else
    349         {
    350             Item maxTail = maxRec(node.next);
    351             return ((Comparable)node.item).compareTo(maxTail) > 0 ? node.item : maxTail;
    352         }
    353     }
    354     
    355     /*****************
    356      * Exercise 1.3.30
    357      *****************/
    358     public void reverse()
    359     {
    360         first = reverse(first);
    361         setLastAndN();
    362     }
    363     
    364     public Node reverse(Node node)
    365     {
    366         Node srcFirst = node,
    367              destFirst = null;
    368         while (srcFirst != null)
    369         {
    370             Node next = srcFirst.next;
    371             srcFirst.next = destFirst;
    372             destFirst = srcFirst;
    373             srcFirst = next;
    374         }
    375         
    376         return destFirst;
    377     }
    378     
    379     /***************************************
    380      * Recursive solution to Exercise 1.3.30
    381      ***************************************/
    382     public void reverseRec()
    383     {
    384         first = reverseRec(first);
    385         setLastAndN();
    386     }
    387     
    388     private Node reverseRec(Node node)
    389     {
    390         return reverseRec(node, null);
    391     }
    392     
    393     private Node reverseRec(Node srcFirst, Node destFirst)
    394     {
    395         if (srcFirst == null)
    396             return destFirst;
    397         else
    398         {
    399             Node next = srcFirst.next;
    400             srcFirst.next = destFirst;
    401             return reverseRec(next, srcFirst);
    402         }
    403     }
    404         
    405     
    406     /************
    407      * Unit tests
    408      ************/
    409     
    410     private static void testBaseMethods()
    411     {
    412         int[] a = { 2, 4, 6, 8, 10, 12 };
    413         
    414         List<Integer> lst = new List<Integer>();
    415         for (int i = 0; i < a.length; i++)
    416             lst.append(a[i]);
    417         showList(lst);
    418         
    419         lst = new List<Integer>();
    420         for (int i = 0; i < a.length; i++)
    421             lst.prepend(a[i]);
    422         showList(lst);
    423         
    424         StdOut.println("removeFirst: " + lst.removeFirst());
    425         showList(lst);
    426     }
    427     
    428     private static void testRemoveLast()
    429     {
    430         List<Integer> lst = new List<Integer>(new Integer[] { 6, 8, 10, 12 });
    431         showList(lst);
    432         
    433         while (!lst.isEmpty())
    434         {
    435             StdOut.println("removeLast: " + lst.removeLast());
    436             showList(lst);
    437         }
    438     }
    439     
    440     private static void testDelete()
    441     {
    442         List<Integer> lst = new List<Integer>(new Integer[] { 2, 4, 6, 8, 10, 12 });
    443         showList(lst);
    444         
    445         StdOut.printf("delete(%d): %s
    ", 5, lst.delete(5));
    446         showList(lst);
    447         
    448         StdOut.printf("delete(%d): %s
    ", 1, lst.delete(1));
    449         showList(lst);
    450         
    451         StdOut.printf("delete(%d): %s
    ", 4, lst.delete(4));
    452         showList(lst);
    453         
    454         StdOut.printf("delete(%d): %s
    ", 8, lst.delete(8));
    455         showList(lst);
    456         
    457         StdOut.printf("delete(%d): %s
    ", 0, lst.delete(0));
    458         showList(lst);
    459         
    460         while (!lst.isEmpty())
    461         {
    462             StdOut.printf("delete(%d): %s
    ", 1, lst.delete(1));
    463             showList(lst);
    464         }
    465     }
    466     
    467     private static void testContains()
    468     {
    469         Integer[] a = { 4, 6, 10, 12 };
    470         List<Integer> lst = new List<Integer>(a);
    471         showList(lst);
    472         
    473         StdOut.printf("contains(%d): %s
    ", 0, lst.contains(0));
    474         
    475         for (int i = 0; i < a.length; i++)
    476             StdOut.printf("contains(%d): %s
    ", a[i], lst.contains(a[i]));
    477     }
    478     
    479     private static void testRemove()
    480     {
    481         for (int k = 0; k < 8; k++)
    482         {
    483             List<Integer> lst1 = randomList(20, 0, 5);
    484             List<Integer> lst2 = new List<Integer>(lst1);
    485             StdOut.println(lst1);
    486             StdOut.println();
    487             
    488             int n = StdRandom.uniform(0, 5);
    489             
    490             StdOut.printf("remove(%d):
    ", n);
    491             lst1.remove(n);
    492             showList(lst1);
    493             
    494             StdOut.printf("removeRec(%d):
    ", n);
    495             lst2.removeRec(n);
    496             showList(lst2);
    497             StdOut.println();
    498         }
    499     }
    500     
    501     private static void testReverse()
    502     {
    503         int n = 10;
    504         Integer[] a = new Integer[n];
    505         for (int i = 0; i < n; i++)
    506             a[i] = 2 * (i + 1);
    507         
    508         testReverse(new List<Integer>(a));
    509         StdOut.println();
    510         
    511         testReverse(randomList(20, 0, 10));
    512         StdOut.println();
    513         
    514         testReverse(new List<Integer>(new Integer[] { 37 }));
    515         StdOut.println();
    516         
    517         testReverse(new List<Integer>(new Integer[] { }));
    518         StdOut.println();
    519     }
    520     
    521     private static void testReverse(List<Integer> lst)
    522     {
    523         List<Integer> lst1 = lst;
    524         List<Integer> lst2 = new List<Integer>(lst1);
    525         StdOut.println(lst1);
    526         
    527         StdOut.println("reverse():");
    528         lst1.reverse();
    529         StdOut.println(lst1);
    530         
    531         StdOut.println("reverseRec():");
    532         lst2.reverseRec();
    533         StdOut.println(lst2);
    534     }
    535     
    536     private static void testNode()
    537     {
    538         List<Integer> lst = new List<Integer>(new Integer[] { 2, 6, 12 });
    539         showList(lst);
    540         
    541         for (int i = -1; i <= 4; i++)
    542             StdOut.printf("node(%d): %s
    ", i, lst.node(i) != null ? lst.node(i).item : null);
    543     }
    544     
    545     private static void testRemoveAfter()
    546     {
    547         List<Integer> lst = new List<Integer>(new Integer[] { 2, 6, 8, 10, 12 });
    548         showList(lst);
    549         
    550         int[] k = { 0, 2, 1, 5, 3, 2, 1 };
    551         
    552         for (int i = 0; i < k.length; i++)
    553         {
    554             StdOut.printf("removeAfter(node(%d)):
    ", k[i]);
    555             lst.removeAfter(lst.node(k[i]));
    556             showList(lst);
    557         }
    558     }
    559     
    560     private static void testInsertAfter()
    561     {
    562         List<Integer> lst = new List<Integer>(new Integer[] { 2, 6, 10, 12 });
    563         showList(lst);
    564         
    565         StdOut.printf("insertAfter(node(%d), null):
    ", 1);
    566         lst.insertAfter(lst.node(1), null);
    567         showList(lst);
    568         
    569         int ia = 1,
    570             b = 3;
    571         StdOut.printf("insertAfter(node(%d), createNode(%d)):
    ", ia, b);
    572         lst.insertAfter(lst.node(ia), lst.createNode(b));
    573         showList(lst);
    574         
    575         ia = 5;
    576         b = 25;
    577         StdOut.printf("insertAfter(node(%d), createNode(%d)):
    ", ia, b);
    578         lst.insertAfter(lst.node(ia), lst.createNode(b));
    579         showList(lst);
    580     }
    581     
    582     private static void testMax()
    583     {
    584         for (int k = 0; k < 8; k++)
    585         {
    586             List<Integer> lst = randomList(10, 100, 1000);
    587             StdOut.println(lst);
    588             
    589             StdOut.printf("max():    %d
    ", lst.max(lst.node(1)));
    590             StdOut.printf("maxRec(): %d
    
    ", lst.maxRec(lst.node(1)));
    591         }
    592     }
    593     
    594     
    595     /*******************
    596      * Unit test helpers
    597      *******************/
    598     
    599     public static void showList(List lst)
    600     {
    601         StdOut.println(lst);
    602         if (!lst.isEmpty())
    603             StdOut.printf("Size: %d, First: %s, Last: %s
    
    ", lst.size(), lst.first(), lst.last());
    604         else
    605             StdOut.printf("Size: %d
    
    ", lst.size());
    606     }
    607     
    608     private static List<Integer> randomList(int n, int a, int b)
    609     {
    610         Integer[] r = new Integer[n];
    611         for (int i = 0; i < n; i++)
    612             r[i] = StdRandom.uniform(a, b);
    613         return new List<Integer>(r);
    614     }
    615     
    616     public static void main(String[] args)
    617     {
    618         testBaseMethods();
    619         StdOut.println();
    620         
    621         testRemoveLast();
    622         StdOut.println();
    623         
    624         testDelete();
    625         StdOut.println();
    626         
    627         testContains();
    628         StdOut.println();
    629         
    630         testNode();
    631         StdOut.println();
    632         
    633         testRemoveAfter();
    634         StdOut.println();
    635         
    636         testInsertAfter();
    637         StdOut.println();
    638         
    639         testRemove();
    640         StdOut.println();
    641         
    642         testMax();
    643         StdOut.println();
    644         
    645         testReverse();
    646         StdOut.println();
    647     }
    648 }
  • 相关阅读:
    案例分析:设计模式与代码的结构特性——高级软件工程课第六次作业
    用例建模Use Case Modeling——高级软件工程第四次作业
    分析一套源代码的代码规范和风格并讨论如何改进优化代码——高级软件工程课第三次作业
    结合工程实践选题调研分析同类软件产品——高级软件工程课第二次作业
    如何提高程序员的键盘使用效率?——高级软件工程课第一次作业
    ping命令研究报告——网络程序设计课第一次作业
    业务领域建模Domain Modeling——高级软件工程课第五次作业
    Windbg Symbol问题
    堆和栈的区别 (转贴)
    VS2008编译驱动文件设置_不用DDKWizard
  • 原文地址:https://www.cnblogs.com/shamgod/p/5409168.html
Copyright © 2020-2023  润新知