08年9月入学,12年7月毕业,结束了我在软件学院愉快丰富的大学生活。此系列是对四年专业课程学习的回顾,索引参见:http://blog.csdn.net/xiaowei_cqu/article/details/7747205
链式栈各种基本运算算法的实现
栈是只能在某一端插入和删除的特殊线性表。它按照后进先出的原则存储数据,先进入的数据被压入栈底(push),最后的数据在栈顶(top),需要读数据的时候从栈顶开始弹出数据(top)最后一个数据被第一个读出来。
链式栈中的元素以Node的形式存储,节点Node中存有此节点存于栈中的元素以及指向下个节点的指针。链式栈的数据成员只用保存指向栈顶节点的指针 *top_node.
因为指针的运用,链式栈在实现时尤其重要的一点就是编写自己的析构函数,拷贝构造函数和重载赋值运算符。
【实验说明】
我选择的题目是测试链式栈的各种功能
1.链式栈中元素以节点形式存储,首先编写结构Node的定义和实现。
2.编写栈的定义和实现。栈中数据成员是指向栈顶的指针*top_node。成员函数是实现栈最基本的操作——push()向栈中加入元素,pop()移出栈顶元素,top()得到栈顶元素,empty()判断栈是否为空。
3.编写链式栈的析构函数~Stack(),拷贝构造函数Stack(const Stack &original),重载赋值运算符operator=(const Stack &original);
4.编写用于测试栈的各种功能的函数 do_comman()和get_command()以及一些辅助的介绍函数introduction(),help()。
5.编写主函数。运行并测试栈的各种功能。
【相关代码】
node.h
#ifndef NODE_H
#define NODE_H
#include<iostream>
using namespace std;
enum Error_code{success,overflow,underflow};
typedef char Node_entry;
struct Node{
//data members
Node_entry entry;
Node *next;
//constructors
Node();
Node(Node_entry item,Node *add_on=NULL);
};
#endif
node.cpp
#include "node.h"
Node::Node()
{
next=NULL;
}
Node::Node(Node_entry item, Node *add_on)
{
entry=item;
next=add_on;
}
linked_stack.h
#ifndef LINKEDSTACK_H
#define LINKEDSTACK_H
#include "node.h"
typedef char Stack_entry;
class Stack{
public:
//constructor
Stack();
//member functions
bool empty()const;
Error_code push(const Stack_entry &item);
Error_code pop();
Error_code top(Stack_entry &item)const;
//destructor
~Stack();
//copy constructor
Stack(const Stack &original);
//overload assignment
void operator=(const Stack &original);
protected:
//data member
Node *top_node;
};
#endif
linked_stack.cpp
#include "linked_stack.h"
//constructor
Stack::Stack(){
top_node=NULL;
}
//function empty() to check if the stack is empty
bool Stack::empty() const{
if(top_node==NULL)
return true;
else
return false;
}
//function pushh(const Stack_entry &item) to push item into the stack
Error_code Stack::push(const Stack_entry &item)
{
Node *new_top=new Node(item,top_node);
if(new_top==NULL)
return overflow;
top_node=new_top;
return success;
}
//function pop() to pop the last item int the stack
Error_code Stack::pop()
{
Node *old_top=top_node;
if(top_node==NULL)
return underflow;
top_node=old_top->next;
delete old_top;
return success;
}
//function top(Stack_entry &item) to assig item with the top item in the stack
Error_code Stack::top(Stack_entry &item)const{
if(top_node==NULL)
return underflow;
item=top_node->entry;
return success;
}
//destructor
Stack::~Stack()
{
while(!empty())
pop();
}
//overload assignment
void Stack::operator=(const Stack &original)
{
Node *new_top,*new_copy,*original_node=original.top_node;
if(original_node==NULL)new_top=NULL;
else{
new_copy=new_top=new Node(original_node->entry);
while(original_node->next!=NULL){
original_node=original_node->next;
new_copy->next=new Node(original_node->entry);
new_copy=new_copy->next;
}
}
while(!empty())
pop();
top_node=new_top;
}
//copy constructor
Stack::Stack(const Stack &original)
{
Node *new_copy,*original_node=original.top_node;
if(original_node==NULL)
top_node=NULL;
else{
top_node=new_copy=new Node(original_node->entry);
while(original_node->next!=NULL){
original_node=original_node->next;
new_copy->next=new Node(original_node->entry);
new_copy=new_copy->next;
}
}
}
【过程记录】
实验截图:
【结果分析】
1.链式栈中以节点的形式存储栈中的元素,每个节点Node由要保存的元素entry和指向下一个节点的指针next组成。这样大大避免了由连续数组实现栈所带来的限制——不用从一开始就限定栈可存储元素的大小,在添加新的元素时再申请空间,而且节省了不必要的空间。因为节点的存储在物理结构上不一定是连续的,只有内存不足时才会达到full的状态(通常情况是够用的)。
2.指针的运用是件巧妙而又危险的工作。在每改变一个元素(添加或删除)都应注意指针知否指向了正确的地址,避免悬空指针和内存泄露。
3.因为指针的运用,编写Stack类时必须编写自己析构函数,拷贝构造函数以及赋值操作符。
分享到:
相关推荐
本文将深入探讨一种特殊的数据结构——栈(Stack),特别是在链式栈(Linked Stack)中的应用。栈是一种线性数据结构,它遵循“后进先出”(Last In, First Out,简称LIFO)的原则,形象地比喻为一个堆叠的盘子,...
**链式队列**(Linked Queue)是另一种线性数据结构,但与栈不同,它遵循“先进先出”(First In, First Out,简称FIFO)原则。队列的主要操作包括入队(Enqueue)新元素到队尾和出队(Dequeue)队首元素。链式队列...
首先,让我们来理解一下栈(Stack)这个数据结构。栈被称为“后进先出”(Last In First Out,简称LIFO)的数据结构,它的主要操作包括压入(Push)和弹出(Pop)。压入操作是将元素添加到栈顶,而弹出操作则从栈顶...
顺序栈的效率在元素插入和删除时取决于元素的位置,而在链式栈中,这些操作通常只与栈顶元素有关,因此速度较快。然而,顺序栈在空间利用率上可能更优,因为不需要额外的指针结构。 在处理栈溢出问题时,一种策略是...
链式栈则通过链表节点来存储元素,每个节点包含元素值和指向下一个节点的指针。 队列(Queue)是另一种线性数据结构,遵循“先进先出”(FIFO,First In First Out)原则,元素的插入在队尾,删除在队头。队列在...
栈中数据成员是指向栈顶的指针*top_node。成员函数是实现栈最基本的操作——push()向栈中加入元素,pop()移出栈顶元素,top()得到栈顶元素,empty()判断栈是否为空。 参见博客:...
在C++编程中,栈(Stack)是一种非常重要的数据结构,它遵循“后进先出”(LIFO,Last In First Out)的原则。栈结构在许多计算机算法和系统设计中都有广泛应用,例如函数调用、表达式求解、深度优先搜索等。 栈的...
本文将详细介绍如何利用C++中的类模板来实现两种基本的数据结构:数组栈(Array-based Stack)与链式栈(Linked Stack)。这些通用的数据结构能够为开发人员提供灵活且高效的解决方案。 #### 类模板概述 类模板是...
【数据结构】中的栈(Stack)与队列(Queue) 栈是数据结构中的一种基本类型,它遵循“后进先出”(LIFO,Last In, First Out)的原则。在栈中,插入(Push)和删除(Pop)操作只允许在列表的末尾进行,这个位置被...
在这个C++程序中,我们使用了一个链式栈(Linked Stack)来存储和处理表达式中的操作符和操作数。链式栈是通过链表实现的栈数据结构,它可以动态地分配和释放内存,以适应不同大小的数据。 首先,我们定义了一个...
本单元主要关注两种特殊的数据结构——栈和队列,它们都是线性数据结构的变体,但有着特定的操作规则。以下是这些知识点的详细说明: **1. 栈(Stack)** 栈是一种后进先出(LIFO, Last In First Out)的数据结构。...
3. **单项列表**(Singly Linked List):是最基本的链式数据结构,每个节点包含数据和指向下一个节点的引用。"单项列表.html"将展示如何实现基本的添加、删除和遍历操作。 4. **哈希表**(Hash Table):通过散列...
本章主要探讨的是两种常用且基础的数据结构——栈(Stack)和队列(Queue),以及它们的两种基本存储方式:顺序存储结构(Sequential Storage Structure)和链式存储结构(Linked Storage Structure)。我们将深入...
链式队列(Linked Queue)则是使用链表作为底层数据结构的队列,相比于数组实现,链式队列在插入和删除元素时更灵活,不需要考虑数组的容量问题。链表节点包含数据和指向下一个节点的指针,因此在队列的尾部添加元素...
3. **链表(Linked List)**:链表是一种常见的数据结构,由一系列节点组成,每个节点包含数据和指向下一个节点的指针。 - 单链表:每个节点只有一个指向下一个节点的指针。 - 双向链表:每个节点有两个指针,一个...
在本章中,我们将专注于两种特殊类型的线性数据结构——栈和队列,它们在逻辑上属于线性表,但在操作上具有特定的限制。 **栈(Stack)** 栈是一种“后进先出”(LIFO, Last In First Out)的数据结构,形象地比喻...
链表(Linked List):链表是一种数据元素按照链式存储结构进行存储的数据结构,这种存储结构具有在物理上存在非连续的特点。 树(Tree):树是典型的非线性结构,它是包括,2 个结点的有穷集合 K。 图(Graph):图...
同时,书中还介绍了栈和队列的链式实现和数组实现,帮助学生理解数据结构的不同表示方式及其优缺点。 ### 4. 树(Tree) 树是一种非线性数据结构,它由一个根节点和若干子树构成,子树本身也是一个树。在耿国华版的...
根据提供的信息来看,这份文档似乎并未包含实际的“广东工业大学《数据结构》复习题(含答案)”的具体内容,而是重复出现了一些不明的文字“创创大帝”。因此,基于现有信息,我们将围绕“数据结构”这一核心主题...