ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

【LeetCode】剑指 Offer 09. 用两个栈实现队列

2020-07-11 16:02:45  阅读:207  来源: 互联网

标签:09 obj Offer int ptStack Stack return data LeetCode


【题目描述】

用两个栈实现一个队列。队列的声明如下,请实现它的两个函数 appendTail 和 deleteHead ,分别完成在队列尾部插入整数和在队列头部删除整数的功能。(若队列中没有元素,deleteHead 操作返回 -1 )

示例 1:

输入:
["CQueue","appendTail","deleteHead","deleteHead"]
[[],[3],[],[]]
输出:[null,null,3,-1]
示例 2:

输入:
["CQueue","deleteHead","appendTail","appendTail","deleteHead","deleteHead"]
[[],[],[5],[2],[],[]]
输出:[null,-1,null,null,5,2]
提示:

1 <= values <= 10000
最多会对 appendTail、deleteHead 进行 10000 次调用

来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/yong-liang-ge-zhan-shi-xian-dui-lie-lcof

【解题思路】

用两个栈实现队列:

  • 栈无法实现队列功能: 栈底元素(对应队首元素)无法直接删除,需要将上方所有元素出栈。
  • 双栈可实现列表倒序: 设有含三个元素的栈 A = [1,2,3] 和空栈 B = []。若循环执行 A 元素出栈并添加入栈 B ,直到栈 A 为空,则 A = [] , B = [3,2,1],即 栈 B 元素实现栈 A 元素倒序 。
  • 利用栈 B 删除队首元素: 倒序后,B 执行出栈则相当于删除了 A 的栈底元素,即对应队首元素。

【提交代码】

  1 typedef struct st_stack{
  2     int size;
  3     int *data;
  4     int top;    
  5 }T_Stack;
  6 
  7 typedef struct {
  8     T_Stack *s1;
  9     T_Stack *s2;
 10 } CQueue;
 11 
 12 
 13 int StackInit( T_Stack *ptStack, int *data, int size)
 14 {
 15     ptStack->size = size;
 16     ptStack->data = data;
 17     ptStack->top = 0;
 18 
 19     return 0;
 20 }
 21 
 22 int StackPush( T_Stack *ptStack, int data )
 23 {
 24     if( ptStack->top == ptStack->size )
 25     {
 26         return -1;
 27     }
 28     
 29     ptStack->data[ptStack->top++] = data;
 30 
 31     return 0;
 32 }
 33 
 34 int StackPop( T_Stack *ptStack, int *data )
 35 {
 36     if( ptStack->top == 0 )
 37     {
 38         return -1;
 39     }
 40 
 41     *data = ptStack->data[--ptStack->top];
 42 
 43     return 0;
 44 }
 45 
 46 int StackTop( T_Stack *ptStack, int *data )
 47 {
 48     if( ptStack->top == 0 )
 49     {
 50         return -1;
 51     }
 52 
 53     *data = ptStack->data[ptStack->top - 1];
 54 
 55     return 0;
 56 }
 57 
 58 int StackIsEmpty( T_Stack *ptStack )
 59 {
 60     return ( ptStack->top == 0 );
 61 }
 62 
 63 int StackIsFull( T_Stack *ptStack )
 64 {
 65     return ( ptStack->top == ptStack->size );
 66 }
 67 
 68 #define QUEUE_SIZE_MAX      ( 10000 )
 69 
 70 CQueue* cQueueCreate() {
 71     int *data1;
 72     int *data2;
 73     T_Stack *s1;
 74     T_Stack *s2;
 75     CQueue *queue;
 76 
 77     data1 = (int *)malloc( sizeof(int) * QUEUE_SIZE_MAX );
 78     data2 = (int *)malloc( sizeof(int) * QUEUE_SIZE_MAX );
 79 
 80     s1 = (T_Stack *)malloc( sizeof(T_Stack));
 81     s2 = (T_Stack *)malloc( sizeof(T_Stack));
 82 
 83     StackInit( s1, data1, QUEUE_SIZE_MAX );
 84     StackInit( s2, data2, QUEUE_SIZE_MAX );
 85 
 86     queue = (CQueue *)malloc( sizeof(CQueue) );
 87 
 88     queue->s1 = s1;
 89     queue->s2 = s2;
 90 
 91     return queue;
 92 }
 93 
 94 int cQueueAppendTail(CQueue* obj, int value) {
 95     if( StackIsFull( obj->s1) ) 
 96     {
 97         return -1;
 98     }
 99 
100     if( StackPush( obj->s1, value ) != 0 )
101     {
102         return -1;
103     }
104 
105     return 0;
106 }
107 
108 int cQueueDeleteHead(CQueue* obj) {
109     int tmp;
110 
111     // 1.当B不为空,则B中仍有已完成倒叙的元素,因此直接返回B的栈顶元素
112     if( !StackIsEmpty( obj->s2 ) )
113     {
114         if( StackPop( obj->s2, &tmp ) != 0)
115         {
116             return -1;
117         }
118 
119         return tmp;
120     }
121 
122     // 2.当A也为空,则两个栈都为空,无元素,因此返回-1
123     if( StackIsEmpty( obj->s1 ) )
124     {
125         return -1;
126     }
127 
128     // 3.将A元素全部转移至栈B中,实现元素倒叙,并返回栈B的栈顶元素
129     while( !StackIsEmpty( obj->s1) && !StackIsFull( obj->s2 ) )
130     {
131         StackPop( obj->s1, &tmp );
132         StackPush( obj->s2, tmp );
133     }
134 
135     if( !StackIsEmpty( obj->s1) ) // 如果A没有完全转移,则还是错误的
136     {
137         return -1;
138     }
139 
140     StackPop( obj->s2, &tmp );
141 
142     return tmp;
143 }
144 
145 void cQueueFree(CQueue* obj) {
146     free(obj->s1->data);
147     free(obj->s2->data);
148     free(obj->s1);
149     free(obj->s2);
150     free(obj);
151 }
152 
153 /**
154  * Your CQueue struct will be instantiated and called as such:
155  * CQueue* obj = cQueueCreate();
156  * cQueueAppendTail(obj, value);
157  
158  * int param_2 = cQueueDeleteHead(obj);
159  
160  * cQueueFree(obj);
161 */

 

标签:09,obj,Offer,int,ptStack,Stack,return,data,LeetCode
来源: https://www.cnblogs.com/utank/p/13283989.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有