码迷,mamicode.com
首页 > 编程语言 > 详细

算法导论之八(10.1-5单数组实现双端队列)

时间:2015-01-02 23:45:19      阅读:366      评论:0      收藏:0      [点我收藏+]

标签:算法导论   遍历   双端队列      

算法导论第三版P131

题目:

10.1-5 栈插入和删除元素只能在同一端进行,队列的插入操作和删除操作分别在两端进行,与它们不同的,有一种双端队列(deque),其插入和删除操作都可以在两端进行。写出4个时间均为O(1)的过程,分别实现在双端队列插入和删除元素的操作,该队列使用一个数组实现的。


注意点:

1、左右端点指向的位置是类似于队列中的tail端点,是下一个插入操作的位置。

2、然后注意遍历的时候,左端点和右端点的位置关系,有两种可能,所以遍历的方式不一样。


代码:

/*
 * 使用单数组实现双端队列
 */
#include <iostream>

using namespace std;

class deque {
	int leftHead; //左端节点,指向下一个能操作的空位置
	int rightHead; //右端节点
	int len;
	int* array;
public:
	deque(int size) :
			leftHead(0), rightHead(0), len(size) {
		array = new int[size];
	}

	~deque() {
		delete array;
		leftHead = rightHead = 0;
	}

	/*
	 * 获取上一个位置
	 */
	int pre(int pos) {
		if (pos == 0) {
			return len - 1;
		} else {
			return --pos;
		}
	}

	/*
	 * 获取下一个位置
	 */
	int next(int pos) {
		if (pos == len - 1) {
			return 0;
		} else {
			return ++pos;
		}
	}
	bool isEmpty() {
		return leftHead == rightHead ? true : false;
	}

	/*
	 * 左边节点的插入
	 */
	void leftInsert(int k) {
		int p = pre(leftHead);
		if (p == rightHead) {
			cout << "error:overflow" << endl;
			return;
		}

		//如果是空的情况,则左右节点都需要移动
		if (isEmpty()) {
			rightHead = next(rightHead);
		}
		array[leftHead] = k;
		leftHead = p;
	}

	void rightInsert(int k) {
		int n = next(rightHead);
		if (n == leftHead) {
			cout << "error:oveflow" << endl;
			return;
		}
		//如果是空的情况,则左右节点都需要移动
		if (isEmpty()) {
			leftHead = pre(leftHead);
		}
		array[rightHead] = k;
		rightHead = next(rightHead);
	}

	/*
	 * 左端删除
	 */
	int leftDelete() {
		if (isEmpty()) {
			cout << "error:underflow" << endl;
			return -1;
		}
		leftHead = next(leftHead);
		//如果只有一个元素,则删除完之后,右端点也要移动,因为这时队列为空了
		if (leftHead == pre(rightHead)) {
			rightHead = leftHead;
		}
		return array[leftHead];
	}

	/*
	 * 右端删除
	 */
	int rightDelete() {
		if (isEmpty()) {
			cout << "error:underflow" << endl;
			return -1;
		}
		rightHead = pre(rightHead);
		//如果只有一个元素,则删除完之后,左端点也要移动,因为这时队列为空了
		if (rightHead == next(leftHead)) {
			leftHead = rightHead;
		}
		return array[rightHead];
	}

	void printDeque() {

		cout << "leftHead=" << leftHead << ",rightHead=" << rightHead << endl;

		if (isEmpty()) {
			return;
		}
		//考虑leftHead和rightHead分别在左右的两种情况
		if (leftHead < rightHead) {
			for (int i = leftHead + 1; i < rightHead; i++) {
				cout << "array[" << i << "]=" << array[i] << ' ';
			}
			cout << endl;
		} else {
			//leftHead > rightHead时的情况
			for (int i = 0; i < rightHead; i++) {
				cout << "array[" << i << "]=" << array[i] << ' ';
			}
			for (int i = leftHead + 1; i < len; i++) {
				cout << "array[" << i << "]=" << array[i] << ' ';
			}
			cout << endl;
		}

	}

};

int main() {

	deque* dq = new deque(5);
	dq->leftDelete();
	dq->leftInsert(4);
	dq->rightInsert(6);
	dq->printDeque();
	cout << dq->leftDelete() << endl;
	dq->printDeque();

	return 0;
}


算法导论之八(10.1-5单数组实现双端队列)

标签:算法导论   遍历   双端队列      

原文地址:http://blog.csdn.net/cyp331203/article/details/42346363

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!