DS博客作业02--栈和队列

这个作业属于哪个班级 数据结构--网络2011/2012
这个作业的地址 DS博客作业02--栈和队列
这个作业的目标 学习栈和队列的结构设计及运算操作
姓名 王历

0 PTA得分截图

1.本周学习总结(0-5分)

1.1 栈

画一个栈的图形,介绍如下内容。

  • 顺序栈的结构、操作函数

** 1)初始化栈initStack(&s)**

void InitStack(SqStack * &s)
  {
      s = (SqStack * )malloc(sizeof(SqStack));
      s->top = -1;
  }

2)销毁栈DestroyStack(&s)

void DestroyStack(SqStack * &s)
  {
      free(s);
  }

3)判断栈是否为空StackEmpty(s)

bool StackEmpty(SqStack *s)
  {
      return(s->top == -1);
  }

4)进栈Push(&s,e)

bool Push(SqStack * &s,Elemtype e)
  {
      if(s->top == MaxSize - 1)
          return false;
      s->top++;
      s->data[s->top] = e;
      return true;
  }

5)出栈Pop(&s,&e)

bool Pop(SqStack *&s,Elemtype &e)
  {
      if(s-> top ==-1)
      return false;
      e = s->data[s->top];
      s->top--;
      return true;
  }

6)取栈顶元素GetTop(d, &e)

bool GetTop(SqStack *s,Elemtype &e)
  {
      if(s->top == -1)
      return false;
      e = s->data[s->top];
      return true;
  }
  • 链栈的结构、操作函数

1)初始化栈initStack(&s)

void InitStack(LinkStNide * &s)
  {
      s = (LinkStNide *)malloc(sizeof(LinkStNide ));
      s->next = NULL;
  }

2)销毁栈DestroyStack(&s)

void DestroyStack(SqStack * &s)
  {
      LinkStNode * pre = s, *p = s->next;
      while(p != NULL)
        {
            free(pre);
            pre = p;
            p = pre->next;
        }
      free(pre);
  }

3)判断栈是否为空StackEmpty(s)

bool StackEmpty(SqStack *s)
  {
      return(s->next == NULL);
  }

4)进栈Push(&s,e)

bool Push(SqStack * &s,Elemtype e)
  {
      LinkStNode *p;
      p = (LinkStNode *)malloc(sizeof(LinkStNode ));
      p->data = e;
      p->next = s->next;
      s->next = p;
  }

5)出栈Pop(&s,&e)

bool Pop(SqStack *&s,Elemtype &e)
  {
      LinkkStNode *p;
      if(s->next == NULL)
          return false;
      p = s->next;
      e = p->data;
      s->next = p->next;
      free(p);
      return true;
  }

6)取栈顶元素GetTop(d, &e)

bool GetTop(SqStack *s,Elemtype &e)
  {
      if((s->next == NULL)
      return false;
      e = s->next->data;
      return true;
  }

1.2 栈的应用

  • 表达式

伪代码

while(从exp读取字符ch,ch!='\0')
  {
    ch为数字:将后续的所有数字均依次存放到postexp中,并以字符'#'标识数字串结束;
    ch为左括号'(':将此括号进栈到Optr中;
    ch为右括号')':将Optr中出栈时遇到的第一个左括号'('以前的运算符依次出栈并存放到postexp中,然后将左括号'('出栈;
    ch为'+'或'-':出栈运算符并存放到postexp中,直到栈空或者栈顶为'(',然后将ch进栈;
    ch为'*'或'/':出栈运算符并存放到postexp中,直到栈空或者栈顶为'('、'+'或'-',然后将ch进栈;
  }
若exp扫描完毕,则将Optr中的所有运算符依次出栈并存放到postexp中。

**设置运算符栈类型SqStack中的ElemType为char类型。根据上述原理得到的trans()算法如下:

void trans(char *exp,char postexp[])
{
    char e;
    SqStack *Optr;
    InitStack(Optr);
    int i = 0;
    while(*exp != '\0')
      {
          switch(*exp)
            {
                case'(':
                    Push(Optr,'(');
                    exp++;
                    break;
                case ')':
                    Pop(Optr,e);
                    while(e != '(')
                      {
                          postexp[i++] = e;
                          Pop(Optr,e);
                        }
                    exp++;
                    break;
                case'+':
                case'-':
                  while(!StackEmpty(Optr))
                    {
                        GetTop(Optr,e);
                        if(e != '(')
                          {
                              postexp[i++] = e;
                              Pop(Optr,e);
                           }
                        else
                              break;
                      }
                    Push(Optr,*exp);
                    exp++;
                    break;
                case'*':
                case'/':
                  while(!StackEmpty(Optr))
                    {
                        GetTop(Optr,e);
                        if(e == '*' || e == '/')
                          {
                              postexp[i++] = e;
                              Pop(Optr,e);
                          }
                        else
                              break;
                    }
                  Push(Optr,*exp);
                  exp++;
                  break;
              default:
                while(*exp >= '0' && *exp <= 9)
                  {
                      postexp[i++] = *exp;
                      exp++;
                  }
                postexp[i++] = '#';
      }
    while(!StackEmpty(Optr))
      {
          Pop(Optr,e);
          postexp[i++] = e;
        }
      postexp[i] = '\0';
      DestroyStack(Optr);
}

1.3 队列

画一个队列的图形,介绍如下内容。

  • 顺序队列的结构、操作函数


    1)初始化队列InitQueue(q)
void InitQueue(SqQueue &q)
{
    q = new Queue;
    q -> front = q -> rear = -1;
}

2)销毁队列DestroyQueue(q)

void DestroyQueue(SqQueue &q)
{
    delete q;
}

3)判断队列是否为空QueueEmpty(q)

bool QueueEmpty(SqQueue q)
{
    return(q ->front == q->rear);
}

4)进队列enQueue(q,e)

bool enQueue(SqQueue &q,ElemType e)
{
    if(q->rear+1 == MaxSize)
         return false;
    q->rear = q->rear + 1;
    q->data[q->rear] = e;
    return true;
}

5)出队列deQueue(q,e)

bool deQueue(SqQueue &q,Elempty &e)
{
    if(q->front == q->rear)
        return false;
    q->front = q->front + 1;
    e = q->data[q->front];
    return true;
}
  • 环形队列的结构、操作函数
    *
    1)初始化队列InitQueue(q)
void InitQueue(SqQueue &q)
{
    q = new Queue;
    q -> front = q -> rear = 0;
}

2)销毁队列DestroyQueue(q)

void DestroyQueue(SqQueue &q)
{
    delete q;
}

3)判断队列是否为空QueueEmpty(q)

bool QueueEmpty(SqQueue q)
{
    return(q ->front == q->rear);
}

4)进队列enQueue(q,e)

bool enQueue(SqQueue &q,ElemType e)
{
    if(q->rear+1 % MaxSize == q->front) 
        return false;
    q->rear = (q->rear + 1) % MaxSize;
    q->data[q->rear] = e;
    return true;
}

5)出队列deQueue(q,e)

bool deQueue(SqQueue &q,Elempty &e)
{
    if(q->front == q->rear)
        return false;
    e = q->data[q->front];
    q->front = (q->front + 1) % MaxSize;
    return true;
}
  • 链队列的结构、操作函数


    1)链队列初始化
Status InitQueue(LinkQueue &Q)
{
    Q.front = Q.rear = new QNode;
    if(!Q.front)
        exit(OVERFLOW);
    Q.front->next = NULL;
    return OK;
}

2)判断链队列是否为空

Status QueueEmpty(LinkQueue Q)
{
    return(Q.front = Q.rear);
}

3)求链队列的队头元素

Staus GetHead(LinkQueue Q,QElmType &e)
{
    if(Q,front == Q,rear)
        return ERROR;
    e = Q.front->next->data;
    return OK;
}

4)链队列入队

Staus EnQueue(LinkQueue &Q,QElemType e)
{
    p = new QNode;
    if(!p)
        exit(OVERFLOW);
    p->data = e;
    p->next = NULL;
    Q,rear->next = p;
    Q.rear = p;
    return OK;
}

5)链队出队

Staus DeQueue(LinkQueue &Q,QElemType &e)
{
    if(Q.front == Q.rear)
        return ERROR;
    p = Q.front->next;
    e = p->data;
    Q.front->next = p->next;
    if(Q.rear == p)
        Q.rear = Q.front;
    delete p;
    return OK;
}
  • 队列应用,要有具体代码操作。

2.PTA实验作业(4分)

2.1 符号配对

2.1.1 解题思路及伪代码

#include <iostream>
#include <stack>
#include <string>
using namespace std;
stack<char> stk;
char tmp[] = { ')','}',']' };
void output(char ch) 
{
    if (ch == '<') 
    {
        cout << "NO\n/*-?" << endl;
    }
    else 
    {
        cout << "NO\n" << ch << "-?" << endl;
    }
}
bool match(char* c, int len) 
{
    int i = -1;
    int j = 0;
    while (++i < len)
    {
        if (c[i] == '/')
        {
            if (stk.empty()) if (c[i + 1] != '*')
                continue;
            if (c[i + 1] == '*')
            {
                stk.push('<');
                ++i;
            }
            else if (stk.top() == '<' && c[i + 1] != '*')
            {
                cout << "NO\n/*-?" << endl;
                return 0;
            }
        }
        else if (c[i] == '*') 
        {
            if (stk.empty()) 
            {
                if (c[i + 1] != '/') 
                    continue;
                else 
                {
                    cout << "NO\n?-*/" << endl;
                    return 0;
                }
            }
            if (stk.top() == '<' && c[i + 1] == '/') 
            {
                stk.pop();
                ++i;
            }
            else if (stk.top() != '<' && c[i + 1] == '/') 
            {
                output(stk.top());
                return 0;
            }
        }
        else if (c[i] == '(' || c[i] == '{' || c[i] == '[')
        {
            stk.push(c[i]);
        }
        else if (c[i] == ')' || c[i] == '}' || c[i] == ']')
        {
            if (stk.empty()) 
            {
                if (c[i] == '}') 
                    j = 1;
                else if (c[i] == ']') 
                    j = 2;
            }
            else 
            {
                if (c[i] == ')') 
                {
                    if (stk.top() == '(') 
                    {
                        stk.pop();
                        continue;
                    }
                    else 
                    {
                        output(stk.top());
                        return 0;
                    }
                }
                else if (c[i] == '}') 
                {
                    if (stk.top() == '{')
                    {
                        stk.pop();
                        continue;
                    }
                    else
                    {
                        output(stk.top());
                        return 0;
                    }
                }
                else 
                {
                    if (stk.top() == '[') 
                    {
                        stk.pop();
                        continue;
                    }
                    else
                    {
                        output(stk.top());
                        return 0;
                    }
                }
            }
            cout << "NO\n?-" << tmp[j] << endl;
            return 0;
        }
    }
    return 1;
}
int main() 
{
    string str;
    while (cin >> str)
    {
        char* c = (char*)str.data();
        if (c[0] == '.' && c[1] == 0)break;
        if (!match(c, str.length())) 
        {
            return 0;
        }
    }
    if (stk.empty()) 
    {
        cout << "YES" << endl;
    }
    else
    {
        if (stk.top() == '<') cout << "NO\n/*-?" << endl;
        else cout << "NO\n" << stk.top() << "-?" << endl;
    }
    return 0;
}

2.2 银行业务队列简单模拟

2.2.1 解题思路及伪代码

#include<stdio.h>
#include<queue>
#include<iostream>
using namespace std;
int main()
{
    int N; cin >> N;
    queue<int>que[2];

    for (int i = 0; i < N; i++)
    {
        int temp; cin >> temp;
        if (temp % 2 == 1)
            que[1].push(temp);
        else 
            que[0].push(temp);
    }
    int flag = 0; 
    for (int time = 1;; time++)
    {
        if (que[0].empty() && que[1].empty())
            break;

        if (!que[1].empty())
        {
            if (flag == 0)
                cout << que[1].front();
            else 
                cout << " " << que[1].front();
            que[1].pop(); flag = 1;
        }
        if (time % 2 == 0 && !que[0].empty())
        {
            if (flag == 0)
                cout << que[0].front();
            else 
                cout << " " << que[0].front();
            que[0].pop(); flag = 1;
        }
    }
    cout << endl;
    return 0;
}

3.阅读代码(0--1分)

posted @ 2021-04-05 22:45  网络2012王历  阅读(48)  评论(0编辑  收藏  举报