您的位置:首页 > 理论基础 > 数据结构算法

数据结构与算法分析课后习题第三章(2)

2007-03-02 21:54 399 查看
希望大家看过后对我自己写的这些笨方法提出意见,如果有问题也请及时指出,谢谢^^

Exercise 3.2 Swap two adjacent elements by adjusting only the links ( and not the data ) using

a. Singly linked list.

b. Doubly linked list 

//single.hpp

#ifndef SINGLE_H__
#define SINGLE_H__

template<typename Object>
class SLList {
private:
 class Node {
 public:
  Node(const Object& ob = Object(), Node* n = 0) :
    data(ob), next(n) {}

 public:
  Node* next;
  Object data;
 };

public:
 class const_iterator {
 public:
  const_iterator() : current(0) {}
  
  const Object& operator*() const{ return retrieve(); }
  const_iterator& operator++()
  {
   current = current->next;
   return *this;
  }

  const_iterator& operator++(int)
  {
   const_iterator old = *this;
   ++(*this);
   return old;
  }

  bool operator==(const const_iterator& rhs) const
  { return current == rhs.current; }
  bool operator!=(const const_iterator& rhs) const
  { return !(*this == rhs); }

 protected:
  const_iterator(Node* p) : current(p) {}

  Object& retrieve() const { return current->data; }
  Node* current;

  friend class SLList<Object>;
 };

 class iterator : public const_iterator {
 public:
  iterator(){}

  Object& operator*() { return retrieve(); }
  const Object& operator*() const { return retrieve(); }

  iterator& operator++()
  {
   current = current->next;
   return *this;
  }

  iterator& operator++(int)
  {
   iterator old = *this;
   ++(*this);
   return old;
  }

  bool operator==(const iterator& rhs)
  { return current == rhs.current; }
  bool operator!=(const iterator& rhs)
  { return !(*this == rhs); }

 private:
  iterator(Node* p) : const_iterator(p){}

  friend class SLList<Object>;
 };

public:
 SLList() { init(); }
 ~SLList()
 {
  clear();
  delete head;
  delete tail;
 }

 SLList(const SLList& rhs)
 {
  init();
  *this = rhs;
 }
 SLList& operator=( const SLList& rhs)
 {
  if(*this == rhs)
   return *this;

  clear();
  for(const_iterator it = rhs.begin(); it != rhs.end(); ++it)
   push_back(*it);

  return *this;
 }

public:
 bool empty() { return theSize == 0; }
 void clear()
 {
  while(!empty())
   pop_front();
 }
 void pop_front()
 { 
  Node* p = head->next;
  head->next = head->next->next;
  delete p;
  --theSize;
 }
 void push_front(const Object& ob)
 { 
  Node* p = head->next;
  head->next = new Node(ob, p);
  ++theSize;
 }

 iterator begin(){ return iterator(head->next); }
 const_iterator begin() const { return const_iterator(head->next); }
 iterator end() { return iterator(tail); }
 const_iterator end() const { return const_iterator(tail); }

 Object& front() { return *begin(); }
 const Object& front() const { return *begin(); }

 void swapAdj(iterator it/*first, iterator second*/)
 {
  int cnt = 0;
  Node* p = it.current;
  iterator i = iterator(this->head);
  while(i != it)
  {
   ++i;
   ++cnt;
  }
   
  --cnt;
  i = iterator(this->head);
  while(cnt > 0)
  {
   ++i;
   --cnt;
  }

  Node* pi = i.current;
  pi->next = p->next;
  p->next = pi->next->next;
  pi->next->next = p;
 }
private:
 Node* head;
 Node* tail;
 unsigned int theSize;

 void init()
 {
  head = new Node();
  tail = new Node();
  head->next = tail;
  tail->next = 0;
  theSize = 0;
 }
};

 

#endif

//double.hpp

//中间加了判断迭代器的功能,应用时该用throw抛出异常来代替现在的cerr

//另,这个判断迭代器功能只用在了insert里,别的懒得写了

#ifndef DOUBLE_HPP__
#define DOUBLE_HPP__

#include <iostream>
#include <cassert>

template<typename Object>
class List {
private:
 class Node {
 public:
  Node(const Object& d = Object(), Node* p = 0, Node* n = 0) : data(d), next(n), prev(p) {}

 public:
  Object data;
  Node* next;
  Node* prev;
 };

public:
 class Const_Iterator {
 public:
  Const_Iterator() : current(0){}

  const Object& operator* () const { return retrieve(); }
  
  Const_Iterator& operator++()
  {
   current = current->next;
   return *this;
  }

  Const_Iterator& operator++(int)
  {
   Const_Iterator old = *this;
   ++(*this);
   return old;
  }

  Const_Iterator& operator--()
  {
   current = current->prev;
   return *this;
  }

  Const_Iterator& operator--(int)
  {
   Const_Iterator old = *this;
   --(*this);
   return old;
  }

  bool operator==(const Const_Iterator& rhs) const
  {
   return current == rhs.current;
  }

  bool operator!=(const Const_Iterator& rhs) const
  {
   return !(*this == rhs);
  }
 protected:
  Node* current;

  Object& retrieve() const { return current->data; }

  Const_Iterator(const List<Object> &lst, Node* p) : theList(&lst), current(p) {}

  void assertValid()
  {
   assert(theList != 0 || current != 0 || current != theList->head);
  }

  const List<Object> *theList;

  friend class List<Object>;

 };

 class Iterator : public Const_Iterator {
 public:
  Iterator(){}
  
  Object& operator*() { return retrieve(); }
  Object& operator*() const { return retrieve(); }

  Iterator& operator++()
  {
   current = current->next;
   return *this;
  }

  Iterator& operator++(int)
  {
   Node old = *this;
   ++(*this);
   return old;
  }

  Iterator& operator--()
  {
   current = current->prev;
   return *this;
  }

  Iterator& operator--(int)
  {
   Node old = *this;
   --(*this);
   return old;
  }

  bool operator==(const Iterator& rhs) const
  {
   return current == rhs.current;
  }

  bool operator!=(const Iterator& rhs) const
  {
   return !(*this == rhs);
  }

 private:
  Iterator(List<Object> &lst, Node *p) : Const_Iterator(lst, p) {}

  friend class List<Object>;

 };

public:
 List()
 {
  init();
 }
 List(const List& rhs)
 {
  init();
  *this = rhs;
 }
 ~List()
 {
  Clear();
  delete head;
  delete tail;
 }
 List& operator=(const List& rhs)
 {
  if(rhs == *this)
   return *this;

  Clear();
  for(Const_Iterator it = rhs.Begin(); it != rhs.End(); ++ it)
   Push_Back(*it);

  return *this;
 }

 Iterator Begin() { return Iterator(*this, head->next); }
 Const_Iterator Begin() const { return Const_Iterator(*this, head->next); }

 Iterator End() { return Iterator(*this, tail); }
 Const_Iterator End() const { return Const_Iterator(*this, tail); }
 
 unsigned int Size() const { return theSize; }
 bool Empty() const { return theSize == 0; }

 void Clear()
 {
  while(!Empty())
   Pop_Front();
 }

 Object& Front() { return *Begin(); }
 const Object& Front() const { return *Begin(); }

 Object& Back() { return *(--End()); }
 const Object& Back() const { return *(--End()); }

 void Push_Front(const Object& ob)
 {
  Insert(Begin(), ob);
 }

 void Push_Back(const Object& ob)
 {
  Insert(End(), ob);
 }

 void Pop_Front() { Erase(Begin()); }
 void Pop_Back() { Erase(--End()); }

 Iterator Insert(Iterator it, const Object& ob)
 {
  it.assertValid();
  if(it.theList != this)
   std::cerr << "Not the same list/n";
  else
  {
   Node* p = it.current;
   ++theSize;
   return Iterator(*this, p->prev = p->prev->next = new Node(ob, p->prev, p));
  }
 }
 Iterator Erase(Iterator it)
 {
  Node* p = it.current;
  Iterator retVal(*this, p->next);
  p->prev->next = p->next;
  p->next->prev = p->prev;
  delete p;
  --theSize;

  return retVal;
 }

 Iterator Erase(Iterator start, Iterator end)
 {
  for(Iterator it = start; it != end; )
   it = Erase(it);
  
  return end;
 }

 void swapAdj(Iterator it)
 {
  Node* first = it.current;
  Node* second = (++it).current;

  second->next->prev = first;
  first->prev->next = second;
  first->next = second->next;
  
  second->prev = first->prev;
  second->next = first;
  first->prev = second;
 }  

private:
 unsigned int theSize;
 Node* head;
 Node* tail;

 void init()
 {
  theSize = 0;
  head = new Node();
  tail = new Node();
  head->next = tail;
  tail->prev = head;
 }
};

#endif

 

//main.cpp

#include "single.hpp"
#include "double.hpp"
#include <iostream>

int main()
{
 //SLList<int> l;
 List<int> dl;
 //l.push_front(2);
 //l.push_front(1);
 //l.push_front(3);

 dl.Push_Back(3);
 dl.Push_Back(2);
 dl.Push_Back(1);

 for(List<int>::Const_Iterator it = dl.Begin(); it != dl.End(); ++it)
  std::cout << *it << std::endl;

 List<int>::Iterator it = dl.Begin();
 ++it;
 dl.swapAdj(it);

 std::cout << "after swap: " << std::endl;

 for(List<int>::Const_Iterator it = dl.Begin(); it != dl.End(); ++it)
  std::cout << *it << std::endl;

 std::cout << "/n";

 for(List<int>::Const_Iterator it = --dl.End(); it != --dl.Begin(); --it)
  std::cout << *it << std::endl;

 return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息