• 圆桌问题 明


    2013-03-23

    圆桌问题:圆桌上围坐着2n个人。其中n个人是好人,另外n个人是坏人。如果从第一个人开始数数,数到第m个人,则立即处死该人;然后从被处死的人之后开始数数,再将数到的第m个人处死…依此方法不断处死围坐在圆桌上的人。试问预先应如何安排这些好人与坏人的座位,能使得在处死n个人之后,圆桌上围坐的剩余的n个人全是好人

    简化版:圆桌上坐着n个人,从第一个开始计数,偶数的人推出,最后剩下那个位置的人。

    思路:数据结构,首先想到了C#提供的System.Collections.IList,思路很简单,foreach IList中每个记录,count用来计数,若count为偶数,删除之。但想到微软面试要用基元类型,想到两种类型:一个是用数组,一个自定义LinkList,而且要实现Iretator模式,下面是数据结构代码:

    View Code
      1 public interface IMyEnumerator<T>
      2 {
      3     int Length { get; }
      4     T Current { get; }
      5     bool MoveNext();
      6     void Reset();
      7     void Remove(T element);
      8 }
      9 
     10 //以数组结构存储数据,Length为实际记录数,Remove一个元素后,其后的记录向前移,Current为当前指向记录
     11 public class SqArray1 : IMyEnumerator<int>
     12 {
     13     int[] _arr;
     14     int _validLength;
     15     int _index;
     16     public SqArray1(int[] arr)
     17     {
     18         _arr = new int[arr.Length];
     19         arr.CopyTo(_arr, 0);
     20         _validLength = arr.Length;
     21         _index = 0;
     22     }
     23     public int Length
     24     {
     25         get { return _validLength; }
     26     }
     27 
     28     public void Remove(int data)
     29     {
     30         for (int i = 0; i < _validLength; i++)
     31         {
     32             if (_arr[i] == data)
     33             {
     34                 for (int j = i; j < _validLength - 1; j++)
     35                 {
     36                     _arr[j] = _arr[j + 1];
     37                 }
     38                 _validLength--;
     39                 //删除了一个记录,index向前移一位使current指向删除记录的前一个记录
     40                 _index = i - 1;
     41             }
     42         }
     43     }
     44     public void Reset()
     45     {
     46         _index = 0;
     47     }
     48     public bool MoveNext()
     49     {
     50         if (_index < _validLength - 1)
     51         {
     52             _index = _index + 1;
     53             return true;
     54         }
     55         return false;
     56 
     57     }
     58     public int Current
     59     {
     60         get { return _arr[_index]; }
     61     }
     62 }
     63 
     64 //以数组结构存储数据,Length为实际记录数,Remove一个元素后,其记录项的值设为0,Current为当前指向记录
     65 public class SqArray2 : IMyEnumerator<int>
     66 {
     67     int[] _arr;
     68     int _validDataNumber;
     69     int _index;
     70 
     71     public SqArray2(int[] arr)
     72     {
     73         _arr = new int[arr.Length];
     74         arr.CopyTo(_arr, 0);
     75         _validDataNumber = _arr.Length;
     76         _index = 0;
     77     }
     78     public int Length
     79     {
     80         get { return _validDataNumber; }
     81     }
     82 
     83     public void Remove(int data)
     84     {
     85         for (int i = 0; i < _arr.Length; i++)
     86         {
     87             if (_arr[i] == data)
     88             {
     89                 _arr[i] = 0;
     90                 _validDataNumber--;
     91                 //因为当前记录被删了,这里需要设置_current,使它指向前一个有效记录
     92             }
     93         }
     94     }
     95     public bool MoveNext()
     96     {
     97         for (int loc = _index + 1; loc < _arr.Length; loc++)
     98         {
     99             if (_arr[loc] != 0)
    100             {
    101                 _index = loc;
    102                 return true;
    103             }
    104         }
    105         return false;
    106     }
    107     public void Reset()
    108     {
    109         for (int loc = 0; loc < _arr.Length; loc++)
    110         {
    111             if (_arr[loc] != 0)
    112             {
    113                 _index = loc;
    114                 break;
    115             }
    116         }
    117     }
    118     public int Current
    119     {
    120         get
    121         {
    122             return _arr[_index];
    123         }
    124     }
    125 }
    126 
    127 public class LNode
    128 {
    129     public LNode Next;
    130     public int Value;
    131     public LNode(int value) : this(value, null) { }
    132     public LNode(int value, LNode next)
    133     {
    134         Next = next;
    135         Value = value;
    136     }
    137 }
    138 //带有头结点的链表结构
    139 public class LinkList : IMyEnumerator<LNode>
    140 {
    141 
    142 
    143     private LNode _head, _tail;
    144     private int _length;
    145     private LNode _current;
    146 
    147     public int Length
    148     {
    149         get { return _length; }
    150     }
    151 
    152     public LinkList()
    153     {
    154         _head = _tail = new LNode(-1);
    155     }
    156     public LinkList(int[] arr)
    157         : this()
    158     {
    159         for (int i = 0; i < arr.Length; i++)
    160         {
    161             Add(arr[i]);
    162         }
    163     }
    164     public void Add(int data)
    165     {
    166         _tail.Next = new LNode(data);
    167         _tail = _tail.Next;
    168         _length++;
    169     }
    170     public LNode Current
    171     {
    172         get
    173         {
    174             return _current;
    175         }
    176     }
    177     public void Remove(LNode lNode)
    178     {
    179         if (_head == null)
    180             throw new ArgumentOutOfRangeException();
    181         else
    182         {
    183             LNode p = _head;
    184             while (p.Next != null)
    185             {
    186                 if (p.Next.Value == lNode.Value)
    187                 {
    188                     _current = p;
    189                     p.Next = p.Next.Next;
    190                     _length--;
    191                     return;
    192                 }
    193                 p = p.Next;
    194             }
    195 
    196         }
    197     }
    198     public bool MoveNext()
    199     {
    200         if (_current.Next != null)
    201         {
    202             _current = Current.Next;
    203             return true;
    204         }
    205         return false;
    206     }
    207 
    208     public void Reset()
    209     {
    210         _current = _head.Next;
    211     }
    212 }

    客户端代码(包括测试数据和算法):

    View Code
     1 public class Program
     2 {
     3     public static void Main(string[] args)
     4     {
     5         //Black box testing (equivalence divsion,bounary value)
     6         int[] arr = new int[] { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11 };
     7         //arr = new int[] { 1, 2, 3, 4 };    //even number
     8         //arr = new int[] { 1, 2, 3, 4, 5 }; //odd number
     9         //arr = new int[] { 1, 3, 2, 4 };    //mix the ordering up
    10         //arr = new int[] { 1, 2, 3, 5 };    //miss a number
    11 
    12         //arr = null;              //array is null
    13         //arr = new int[] { -1 };  //number is negative number
    14         //arr = new int[] { 0 };   //number is zero
    15         //arr = new int[] { int.MaxValue};  //bounary test
    16         //arr = new char[] { 'a',/0 };  //different type
    17 
    18 
    19         SqArray1 myArr = new SqArray1(arr);
    20         Suanfa(myArr);
    21         Console.WriteLine(myArr.Current.ToString());
    22 
    23         Suanfa(myArr);
    24         Console.WriteLine(myArr.Current.ToString());
    25 
    26         LinkList myList = new LinkList(arr);
    27         Suanfa(myList);
    28         Console.WriteLine(myList.Current.Value.ToString());
    29         Console.Read();
    30     }
    31 
    32     public static void Suanfa<T>(IMyEnumerator<T> myList)
    33     {
    34         int count = 0;
    35         while (myList.Length > 1)
    36         {
    37             myList.Reset();
    38             do
    39             {
    40                 count++;
    41                 if (count % 2 == 0)
    42                 {
    43                     myList.Remove(myList.Current);
    44                 }
    45             }
    46             while (myList.MoveNext());
    47         }
    48         myList.Reset();
    49     }
    50 }
  • 相关阅读:
    如何解决MathPage.wll或MathType.dll文件找不到问题
    2-构建模型
    R语言 ur.df函数(2)
    平稳过程趋势项变点的 CUSUV 检验 秦瑞兵,郭娟
    时间序列的弱相依与强相依
    Cent OS|使用httpd发布网页
    C++练习 | 基于栈的中缀算术表达式求值(double类型
    C++练习 | 不使用头插法逆转单链表
    C++练习 | 单链表的创建与输出(结构体格式)
    C++练习 | 最长公共字符串(DP)
  • 原文地址:https://www.cnblogs.com/Ming8006/p/2976917.html
Copyright © 2020-2023  润新知