• 21、栈的应用-就近匹配


    main.c

    /*
    就近匹配,找出不匹配的符号用箭头A标注出来
    这里只写了小括号的匹配
    */
    
    
    #define _CRT_SECURE_NO_WARNING
    #include<stdio.h>
    #include<stdlib.h>
    #include<string.h>
    #include"Stack.h" 
    
    typedef struct MYCHAR {
        StackNode node;
        char* pAddres;
        int index;
    }MyChar;
    
    int IsLeft(char c) {
        return c == '(';
    }
    int IsRight(char c) {
        return c == ')';
    }
    
    MyChar* CreatMyChar(char* p, int index) {
        MyChar* mychar = (MyChar*)malloc(sizeof(MyChar));
        mychar->pAddres = p;
        mychar->index = index;
    
        return mychar;
    }
    void ShowError(char* str, int pos) {
        printf("%s
    ", str);
        for (int i = 0; i < pos; i++) {
            printf(" ");
        }
        printf("A");
    }
    
    int main() {
    
        //char* str1 = "#include<stdio.h> int main(){int a[4][4];int (*p)[4];p=a[0];return 0;}";
        char* str = "1+2+6(desa)ads)e(rfsd)";
    
        //创建栈容器
        LinkStack* stack = InitStack();
    
        char* p = str;
        SElemType* e = (SElemType*)malloc(sizeof(SElemType));
        int index = 0;
        while (*p != '') {
    
            //如果是左括号 直接进栈
            if (IsLeft(*p)) {
                Push(stack, (StackNode*)CreatMyChar(p, index));
            }
            //如果是右括号 从栈顶弹出元素 判断是不是左括号
            if (IsRight(*p)) {
                if (StackLength(stack) > 0) {
                    MyChar* mychar = (MyChar*)GetTop(stack);
                    if (IsLeft(*(mychar->pAddres))) {
                        Pop(stack, e);
                        free(mychar);
                    }
                }
                else {
                    printf("右括号没有匹配的左括号:
    ");
                    ShowError(str, index);
                    break;
                }
    
            }
            p++;
            index++;
        }
    
        while (StackLength(stack) > 0) {
            MyChar* mychar = (MyChar*)GetTop(stack);
            printf("左括号没有匹配的右括号:
    ");
            ShowError(str, mychar->index);
            Pop(stack, e);
            free(mychar);
        }
    
        free(e);
    
        printf("
    ");
        system("pause");
        return 0;
    }

    stack.h

    #ifndef STACK_H
    #define STACK_H
    
    #include<stdio.h>
    #include<stdlib.h>
    #include<string.h>
    
    #define OK 1
    #define ERROR 0
    #define TRUE 1
    #define FALSE 0
    
    typedef void* SElemType;
    typedef int Status;
    //初始化结构
    typedef struct StackNode {
        SElemType data;
        struct StackNode* next;
    }StackNode, *LinkStackPtr;
    
    typedef struct LinkStack {
        StackNode* top;
        int count;
    }LinkStack;
    
    
    //初始化操作,建立一个空栈
    LinkStack* InitStack();
    //将栈清空
    void ClearStack(LinkStack *s);
    //销毁
    void DestoryStack(LinkStack *s);
    //若栈为空,返回TRUE,否则返回false
    Status IsEmpty(LinkStack s);
    //若栈存在且非空,返回S的栈顶元素
    void* GetTop(LinkStack *s);
    //插入元素e为新的栈顶元素
    Status Push(LinkStack *s, SElemType e);
    //若栈不空,则删除S的栈顶元素,用e返回其值,并返回OK,否则返回ERROR
    Status Pop(LinkStack *s, SElemType *e);
    //返回栈S的元素个数
    Status StackLength(LinkStack *s);
    
    //打印
    void PrintfStack(LinkStack *s);
    
    #endif

    stack.c

    #include"Stack.h"
    
    //初始化操作,建立一个空栈
    LinkStack* InitStack() {
        LinkStack *s = (LinkStack*)malloc(sizeof(LinkStack));
        s->count = 0;
        s->top = (StackNode*)malloc(sizeof(StackNode));
        s->top->data = NULL;
        s->top->next = NULL;
        return s;
    }
    //将栈清空
    void ClearStack(LinkStack *s) {
    
    
    }
    //销毁
    void DestoryStack(LinkStack *s) {
        if (s == NULL) {
            return;
        }
        LinkStackPtr p;
        p = s->top;//将栈顶结点赋值给p
        while (p != NULL) {
            LinkStackPtr pNext = p->next;
            free(p);//释放结点p
            p = pNext;
        }
        s->count = 0;
        free(s);
    }
    //若栈为空,返回TRUE,否则返回false
    Status IsEmpty(LinkStack s) {
        if (s.top->next == NULL) {
            return TRUE;
        }
        return FALSE;
    }
    //若栈存在且非空,返回S的栈顶元素
    void* GetTop(LinkStack *s) {
        if (s == NULL) {
            return NULL;
        }
    
        return s->top->data;
    }
    //插入元素e为新的栈顶元素
    Status Push(LinkStack *s, SElemType e) {
        LinkStackPtr a = (LinkStackPtr)malloc(sizeof(StackNode));
        a->data = e;
        a->next = s->top;//把当前的栈顶元素赋给新结点的直接后继
        s->top = a;//将新结点a赋值给栈顶指针
        s->count++;
        return OK;
    }
    //若栈不空,则删除S的栈顶元素,用e返回其值,并返回OK,否则返回ERROR
    Status Pop(LinkStack *s, SElemType *e) {
        StackNode* p;
        if (IsEmpty(*s)) {
            return ERROR;
        }
        *e = s->top->data;
        p = s->top;//将栈顶结点赋值给p
    
        s->top = p->next;//使得栈顶指针下移一位,指向后一结点
        free(p);//释放结点p
    
        s->count--;
        return OK;
    }
    //返回栈S的元素个数
    Status StackLength(LinkStack *s) {
    
        int j = s->count;
        return j;
    }

    VS2015运行结果:

  • 相关阅读:
    一种动态部署JBoss应用的简单方法
    虚拟机启动的一个Bat文件(启动虚拟机.bat)
    Windows 设置了文件夹共享,删除默认Everyone共享,设置其他用户共享之后打不开的问题
    命令按钮怎么直接指定带参数的宏?
    bat延时
    wrapper.java.additional
    win7下vc6.0的安装
    UVA10391
    UVALive3708
    C++红黑树(类模板实现)
  • 原文地址:https://www.cnblogs.com/luanxin/p/9607931.html
Copyright © 2020-2023  润新知