一、介绍

栈是一种数据存储结构,存储的数据具有先进后出的特点。栈一般分为动态栈和静态栈。

静态栈比较好理解,例如用数组实现的栈。动态栈可以用链表来实现。

方式:固定base指针,每次更改top指向入栈的节点,遍历时从top节点遍历即可。

判空:s.top == s.base && s.top == nil && s.base == nil

栈满:s.top - s.base >= s.stackSize

三、图示

初始状态:s.top = s.base = nil,栈顶和栈底指针指向空,分配栈大小为s.stackSize = 4;

入栈状态:s.base不变,s.top = node,栈底指针不变,栈顶指针指向新节点

栈满状态:s.top - s.base >= s.stackSize, 遍历链表,链表的长度等于或大于栈大小

出栈状态:s.base不变,s.top = node->next,  node节点从链表断裂取出,top指针指向node下一个节点

栈空状态:s.top=nil,并将s.base=s.stop。

三、代码

node:

//  Node.h
// 运行时
//
// Created by 夏远全 on 2019/10/16.
// #import <Foundation/Foundation.h> NS_ASSUME_NONNULL_BEGIN @interface Node : NSObject
@property (nonatomic, assign) int data;
@property (nonatomic, strong, nullable) Node *next;
-(instancetype)initWithData:(int)data;
@end NS_ASSUME_NONNULL_END
//  Node.m
// 运行时
//
// Created by 夏远全 on 2019/10/16. #import "Node.h" @implementation Node -(instancetype)initWithData:(int)data {
self = [super init];
if (self) {
self.data = data;
self.next = nil;
}
return self;
} @end

stack:

//
// Stack.h
// 运行时
//
// Created by 夏远全 on 2019/10/16.
// #import <Foundation/Foundation.h>
#import "Node.h" NS_ASSUME_NONNULL_BEGIN /*
特点:栈是先进后出的特点,采用链表实现一个动态栈(静态栈可以用数组实现)。固定base指针,每次更改top指向入栈的节点,遍历时从top节点遍历即可。 链表栈
判空:s.top == s.base && s.top == nil && s.base == nil
栈满:s.top - s.base >= s.stackSize
*/ @interface Stack : NSObject /**
构造一个栈
@return 栈
*/
+(instancetype)constructStack; /**
推入一个节点
@param node 节点
*/
-(void)pushNode:(Node *)node; /**
推出一个节点
*/
-(void)pop; @end NS_ASSUME_NONNULL_END
//
// Stack.m
// 运行时
//
// Created by 夏远全 on 2019/10/16.
// #import "Stack.h" @interface Stack ()
@property (nonatomic, strong) Node *top; //栈顶指针
@property (nonatomic, strong) Node *base; //栈底指针
@property (nonatomic, assign) int stackSize; //栈初始大小
@end @implementation Stack +(instancetype)constructStack
{
Stack *stack = [[Stack alloc] init];
stack.top = stack.base;
stack.stackSize = ;
return stack;
} -(void)pushNode:(Node *)node { //空节点
if (!node) {
NSLog(@"------不能push一个空的节点-------");
return;
} //栈满
if ([self isFull]) {
NSLog(@"------栈已满-------,当前节点node值: %d不能被push", node.data);
[self printStack];
return;
} //修改栈顶指针,确定栈底指针,不会再改变
if ([self isEmpty]) {
self.top = self.base = node;
}
else{
node.next = self.top;
self.top = node;
}
NSLog(@"push入栈的节点:data = %d", node.data);
} -(void)pop { //栈为空
if ([self isEmpty]) {
NSLog(@"------栈已空-------");
return;
} //删除节点,并修改栈顶指针
Node *popNode = self.top;
self.top = popNode.next;
NSLog(@"pop出栈的节点:data = %d",popNode.data); //节点pop完毕
if (self.top == nil) {
self.base = self.top;
NSLog(@"------栈已空-------");
}
} -(BOOL)isEmpty {
return (self.top == self.base && self.top == nil && self.base == nil);
} -(BOOL)isFull { //遍历长度
int size = ;
Node *p = self.top;
while (p != nil) {
size ++;
p = p.next;
}
return size >= self.stackSize;
} -(void)printStack { NSMutableArray *nodes = [NSMutableArray array];
Node *p = self.top;
while (p != nil) {
[nodes addObject:@(p.data)];
p = p.next;
}
NSLog(@"当前栈的所有节点为:%@",[nodes componentsJoinedByString:@"->"]);
} @end

四、打印

-(void)test_DataStructure_Stack {

    /// 构造栈
Stack *stack = [Stack constructStack]; /// 构造元素
Node *node1 = [[Node alloc] initWithData:];
Node *node2 = [[Node alloc] initWithData:];
Node *node3 = [[Node alloc] initWithData:];
Node *node4 = [[Node alloc] initWithData:];
Node *node5 = [[Node alloc] initWithData:];
Node *node6 = [[Node alloc] initWithData:]; /// push时,进去的顺序为: 1、2、3、4、5
[stack pushNode:node1];
[stack pushNode:node2];
[stack pushNode:node3];
[stack pushNode:node4];
[stack pushNode:node5];
[stack pushNode:node6];//node6不能被push进去,栈已满 /// pop时,出来的顺序为: 5、4、3、2、1
[stack pop];
[stack pop];
[stack pop];
[stack pop];
[stack pop];//最后一个节点被pop出来,栈已空
}
-- ::03.214331+ 运行时[:] push入栈的节点:data =
-- ::03.214513+ 运行时[:] push入栈的节点:data =
-- ::03.214620+ 运行时[:] push入栈的节点:data =
-- ::03.214715+ 运行时[:] push入栈的节点:data =
-- ::03.214796+ 运行时[:] push入栈的节点:data =
-- ::03.214878+ 运行时[:] ------栈已满-------,当前节点node值: 6不能被push
-- ::03.215023+ 运行时[:] 当前栈的所有节点为:->->->->
-- ::03.215111+ 运行时[:] pop出栈的节点:data =
-- ::03.215208+ 运行时[:] pop出栈的节点:data =
-- ::03.215508+ 运行时[:] pop出栈的节点:data =
-- ::03.215845+ 运行时[:] pop出栈的节点:data =
-- ::03.216101+ 运行时[:] pop出栈的节点:data =
-- ::03.216429+ 运行时[:] ------栈已空-------

最新文章

  1. LeetCode-70-Climbing Stairs
  2. lesson32 Shopping for food
  3. 使用engine关键字指定该表使用哪个engine
  4. jvm之xms、xmx等参数分析
  5. Android-Volley详解
  6. hdu 4418 Time travel 概率DP
  7. 加深理解UIView,UIResponder,UIController
  8. ThinkPHP - 配置项目结构
  9. 数据库(概念、语法、DBMS、SQL语言:创建数据库、表格,添加、修改、删除数据记录)
  10. PHP 文件下载 浅析
  11. 集群增量会话管理器——DeltaManager
  12. [转]AI+RPA 融合更智能
  13. tomcat配置ssl证书
  14. 【转】Asp.NetMve移除HTTP Header中服務器信息Server、X-AspNet-Version、X-AspNetMvc-Version、X-Powered-By:ASP.NET
  15. Shell脚本常用模板
  16. Oracle可视化工具PL/SQL Developer的安装与配置
  17. Trades FZU - 2281 (贪心)(JAVA)
  18. c 语言笔记 数组1
  19. 买茶叶想到的哪个比较便宜 x1/y1 &gt;x2/y2 x代表多少钱 y代表 多少克 无聊的试炼
  20. list集合去除重复对象的实现

热门文章

  1. EXCEPTION_ACCESS_VIOLATION(0xc0000005)
  2. python之os模块(os.path)
  3. JSON.parse和JSON.stringify方法
  4. 《Google软件测试之道》
  5. office2019专业版激活秘钥 激活码
  6. [译]Vulkan教程(29)组合的Image采样器
  7. Python 变量与运算符
  8. LeetCode 652: 寻找重复的子树 Find Duplicate Subtrees
  9. DEBUG 命令用法
  10. React躬行记(12)——Redux中间件