栈  0.1
数据结构_第3章
Ackermann.hh
Go to the documentation of this file.
1 
12 #ifndef __ACKERMANN_HH__
13 #define __ACKERMANN_HH__
14 
15 #include "Stack.hh"
16 #include <climits>
17 #include <cstdio>
18 #include <cstring>
19 #include <ctime>
20 #include <iomanip>
21 #include <iostream>
22 
31 class Akm_t
32 {
33 private:
40  std::string _name;
41 
51  static int Ackermann(int m, int n);
52 
62  static int AckermannLoop(int m, int n);
63 
68  static void AkmInit() { Akm_deep = deep_max = 0; }
69 
70  static int Akm_deep;
71  static int deep_max;
72 
73 public:
82  Akm_t(std::string name = "name") : _name(name) {}
83 
88  ~Akm_t() = default;
89 
99  static void Akm_loop(int x, int y);
100 
110  static void Akm_rec(int x, int y);
111 };
112 
113 // 静态数据成员需要在类外定义和初始化
114 int Akm_t::Akm_deep = 0;
115 int Akm_t::deep_max = 0;
116 
117 void Akm_t::Akm_loop(int x, int y)
118 {
119  AkmInit();
120 
121  clock_t t;
122  int result;
123 
124  t = clock();
125  result = AckermannLoop(x, y);
126  t = clock() - t;
127 
128  printf("\nAckermannLoop(%i, %i) = %i\n", x, y, result);
129  printf("AckermannLoop(%i, %i) took %ld clicks (%f seconds).\n", x, y, t, ((float)t) / CLOCKS_PER_SEC);
130 }
131 
132 void Akm_t::Akm_rec(int x, int y)
133 {
134  AkmInit();
135 
136  clock_t t;
137  int result;
138 
139  t = clock(); // Returns the processor time consumed by the program.
140  std::cout << "\nCurrent call:\n";
141  result = Ackermann(x, y);
142  std::cout << "Current deep: " << std::scientific << std::setw(10) << std::left << Akm_deep << " Max deep: " << std::setw(10) << deep_max;
143  std::cout << "\nRecursion terminated.\n";
144  t = clock() - t;
145 
146  printf("\nAckermann(%i, %i) = %i\n", x, y, result);
147  printf("Ackermann(%i, %i) took %ld clicks (%f seconds).\n", x, y, t, ((float)t) / CLOCKS_PER_SEC);
148 }
149 
150 int Akm_t::Ackermann(int m, int n)
151 {
152  static time_t begTime = time(nullptr);
153 
155  {
156  ++Akm_t::deep_max;
157  std::cout << "Max deep: " << std::setw(10) << std::left << std::setw(10) << Akm_t::deep_max << "Time(s): " << std::defaultfloat << difftime(time(nullptr), begTime) << '\r';
158  }
159  // std::cout << "Current deep: " << std::setw(10) << std::left << Akm_deep << " Max deep: " << std::setw(10) << deep_max << '\r';
160  // printf("m = %-10.7g n = %-10.7g\r", (float)m, (float)n);
161  // std::cout << "m = " << std::setw(10) << std::left << m << "n = " << std::setw(10) << std::left << n << '\r';
162  if (!m)
163  {
164  --Akm_t::Akm_deep;
165  return n + 1;
166  }
167  if (!n)
168  {
169  --Akm_t::Akm_deep;
170  return Ackermann(m - 1, 1);
171  }
172 
173  int midVal = Ackermann(m, n - 1);
174 
175  --Akm_t::Akm_deep;
176  return Ackermann(m - 1, midVal);
177 }
178 
179 int Akm_t::AckermannLoop(int m, int n)
180 {
181  time_t begTime = time(nullptr);
182 
183  struct SnapShotStruct
184  {
185  int m;
186  int n;
187  int stage;
188  };
189 
190  int retVal;
191 
192  Stack::seqStack<SnapShotStruct> SnapShotStack;
193  SnapShotStruct currentSnapshot{m, n, 0};
194  SnapShotStack.push(currentSnapshot);
195 
196  std::cout << "Current top:\n";
197  while (!SnapShotStack.isEmpty())
198  {
199  currentSnapshot = SnapShotStack.top();
200  SnapShotStack.pop();
201  if ((Akm_t::Akm_deep = SnapShotStack.size()) > Akm_t::deep_max)
202  {
203  ++Akm_t::deep_max;
204  // std::cout << "m = " << std::setw(10) << std::left << currentSnapshot.m << "n = " << std::setw(10) << currentSnapshot.n << " Current deep: " << std::setw(10) << Akm_deep << " Max deep: " << std::setw(10) << deep_max << '\r';
205  std::cout << "Max deep: " << std::setw(10) << std::left << std::setw(10) << Akm_t::deep_max << "Stack size(kB): " << std::setw(10) << SnapShotStack.elemMem() / 1024 << "Time(s): " << difftime(time(nullptr), begTime) << '\r';
206  }
207  // printf("m = %-10.7g n = %-10.7g\r", (float)currentSnapshot.m, (float)currentSnapshot.n);
208  switch (currentSnapshot.stage)
209  {
210  case 0:
211  {
212  if (!currentSnapshot.m)
213  {
214  retVal = currentSnapshot.n + 1;
215  continue;
216  }
217 
218  if (!currentSnapshot.n)
219  {
220  SnapShotStruct newSnapshot{currentSnapshot.m - 1, 1, 0};
221  SnapShotStack.push(newSnapshot);
222  continue;
223  }
224 
225  currentSnapshot.stage = 1;
226  SnapShotStack.push(currentSnapshot);
227  SnapShotStruct newSnapshot{currentSnapshot.m, currentSnapshot.n - 1, 0};
228  SnapShotStack.push(newSnapshot);
229  continue;
230  }
231  break;
232 
233  case 1:
234  {
235  SnapShotStruct newSnapshot{currentSnapshot.m - 1, retVal, 0};
236  SnapShotStack.push(newSnapshot);
237  continue;
238  }
239  break;
240  } // switch
241  } // while
242 
243  std::cout << "Current deep: " << std::scientific << std::setw(10) << std::left << std::setw(10) << Akm_t::Akm_deep << " Max deep: " << std::setw(10) << Akm_t::deep_max << "Stack size(kB): " << std::setw(10) << SnapShotStack.elemMem() / 1024;
244  std::cout << "\nStack's cleared.\n";
245  return retVal;
246 }
247 
248 #endif
Akm_t::Akm_loop
static void Akm_loop(int x, int y)
堆栈版本的Ackermann函数
Definition: Ackermann.hh:117
Akm_t::Akm_rec
static void Akm_rec(int x, int y)
递归版本的Ackermann函数
Definition: Ackermann.hh:132
Stack::seqStack
Definition: seqStack.hxx:37
Stack::seqStack::push
virtual void push(const T &elem)
Definition: seqStack.hxx:86
Stack::seqStack::isEmpty
virtual bool isEmpty() const
Definition: seqStack.hxx:80
Akm_t::AckermannLoop
static int AckermannLoop(int m, int n)
Ackermann函数堆栈模拟递归版本
Definition: Ackermann.hh:179
Stack::seqStack::top
virtual T top() const
Definition: seqStack.hxx:110
Stack::seqStack::pop
virtual T pop()
Definition: seqStack.hxx:104
Akm_t
实现AckerMann函数。
Definition: Ackermann.hh:31
Akm_t::~Akm_t
~Akm_t()=default
Destroy the Akm_t object.
Stack::seqStack::size
int size() const
Definition: seqStack.hxx:128
Akm_t::Akm_deep
static int Akm_deep
记录当前递归深度
Definition: Ackermann.hh:70
Stack::seqStack::elemMem
int elemMem() const
Definition: seqStack.hxx:134
Stack.hh
栈的抽象类
Akm_t::deep_max
static int deep_max
记录最大递归深度
Definition: Ackermann.hh:71
Akm_t::_name
std::string _name
对象标识
Definition: Ackermann.hh:40
Akm_t::AkmInit
static void AkmInit()
初始化类内部的静态计数器
Definition: Ackermann.hh:68
Akm_t::Akm_t
Akm_t(std::string name="name")
Construct a new Akm_t object.
Definition: Ackermann.hh:82
Akm_t::Ackermann
static int Ackermann(int m, int n)
Ackermann函数递归版本
Definition: Ackermann.hh:150