如何找到第一个并遵循语法的值

时间:2015-11-06 13:53:13

标签: grammar

我有以下语法,我想创建第一个&按照表格。如果我有一个非终端的第一个是epsilon的情况,我是否也应该把这个非终端之后的所有终端作为规则?

S-> ABC
A->Aa/aB
B->Bb/epsilon
C->Cc/epsilon

我的问题是: 在C的第一个中我需要得到First(C)= {epsilon,c)和First(B)= {epsilon,b)? 我得到了以下结果,但我认为我还有问题:

  |first|follow
S |a    |$
A |a    |a
B |eps,b|b,a,$
C |eps,c|$

1 个答案:

答案 0 :(得分:-1)

查找以txt FILE格式编写的语法的第一和后续步骤:

    #include<stdio.h>
    #include<string.h>
    #define size 10

    int i,j,l,m,n=0,o,p,nv,z=0,x=0;
    char str[size],temp,temp2[size],temp3[20],*ptr;

    struct prod
    {
        char left_of_non_term[size],right_of_nonTerm[size][size],first[size],fol[size];
        int n;
    }pro[size];



    int main()
    {
        FILE *f;

        for(i=0;i<size;i++)
            pro[i].n=0;

        f=fopen("lab6.txt","r");
        while(!feof(f))
        {
            fscanf(f,"%s",pro[n].left_of_non_term);
            if(n>0)
            {
                if( strcmp(pro[n].left_of_non_term,pro[n-1].left_of_non_term) == 0 )
                {
                    pro[n].left_of_non_term[0]='\0';
                    fscanf(f,"%s",pro[n-1].right_of_nonTerm[pro[n-1].n]);
                    pro[n-1].n++;
                    continue;
                }
            }
            fscanf(f,"%s",pro[n].right_of_nonTerm[pro[n].n]);
            pro[n].n++;
            n++;
        }

        printf("\nGiven Grammar");
        printf("\n-------------\n");
        for(i=0;i<n;i++)
            for(j=0;j<pro[i].n;j++)
                printf("%s = %s\n",pro[i].left_of_non_term,pro[i].right_of_nonTerm[j]);

        pro[0].first[0]='#';
        for(i=0;i<n;i++)
        {
            for(j=0;j<pro[i].n;j++)
            {
                if( pro[i].right_of_nonTerm[j][0]<65 || pro[i].right_of_nonTerm[j][0]>90 )
                {
                    pro[i].first[strlen(pro[i].first)]=pro[i].right_of_nonTerm[j][0];
                }
                else if( pro[i].right_of_nonTerm[j][0]>=65 && pro[i].right_of_nonTerm[j][0]<=90 )
                {
                    temp=pro[i].right_of_nonTerm[j][0];
                    if(temp=='S')
                        pro[i].first[strlen(pro[i].first)]='#';
                    findter();
                }
            }
        }
        printf("-------------");

        printf("\n\nFIRST\n");
        for(i=0;i<n;i++)
        {
            printf("\n%s -> { ",pro[i].left_of_non_term);
            for(j=0;j<strlen(pro[i].first);j++)
            {
                for(l=j-1;l>=0;l--)
                    if(pro[i].first[l]==pro[i].first[j])
                        break;
                if(l==-1)
                    printf("%c ",pro[i].first[j]);
            }
            printf("}");
        }

        for(i=0;i<n;i++)
            temp2[i]=pro[i].left_of_non_term[0];
        pro[0].fol[0]='$';
        for(i=0;i<n;i++)
        {
            for(l=0;l<n;l++)
            {
                for(j=0;j<pro[i].n;j++)
                {
                    ptr=strchr(pro[l].right_of_nonTerm[j],temp2[i]);
                    if( ptr )
                    {
                        p=ptr-pro[l].right_of_nonTerm[j];
                        if(pro[l].right_of_nonTerm[j][p+1]>=65 && pro[l].right_of_nonTerm[j][p+1]<=90)
                        {
                            for(o=0;o<n;o++)
                                if(pro[o].left_of_non_term[0]==pro[l].right_of_nonTerm[j][p+1])
                                        strcat(pro[i].fol,pro[o].first);
                        }
                        else if(pro[l].right_of_nonTerm[j][p+1]=='\0')
                        {
                            temp=pro[l].left_of_non_term[0];
                            if(pro[l].right_of_nonTerm[j][p]==temp)
                                continue;
                            if(temp=='S')
                                strcat(pro[i].fol,"$");
                            findfol();
                        }
                        else
                            pro[i].fol[strlen(pro[i].fol)]=pro[l].right_of_nonTerm[j][p+1];
                    }
                }
            }
        }

        printf("\n\n\n");
        for(i=0;i<n;i++)
        {
            printf("\nFOLLOW (%s) -> { ",pro[i].left_of_non_term);
            for(j=0;j<strlen(pro[i].fol);j++)
            {
                for(l=j-1;l>=0;l--)
                    if(pro[i].fol[l]==pro[i].fol[j])
                        break;
                if(l==-1)
                    printf("%c",pro[i].fol[j]);
            }
             printf(" }");
        }
        printf("\n");
        //getch();
    }

    void findter()
    {
        int k,t;
        for(k=0;k<n;k++)
        {
            if(temp==pro[k].left_of_non_term[0])
            {
                for(t=0;t<pro[k].n;t++)
                {
                    if( pro[k].right_of_nonTerm[t][0]<65 || pro[k].right_of_nonTerm[t][0]>90 )
                        pro[i].first[strlen(pro[i].first)]=pro[k].right_of_nonTerm[t][0];
                    else if( pro[k].right_of_nonTerm[t][0]>=65 && pro[k].right_of_nonTerm[t][0]<=90 )
                    {
                        temp=pro[k].right_of_nonTerm[t][0];
                        if(temp=='S')
                            pro[i].first[strlen(pro[i].first)]='#';
                        findter();
                    }
                }
                break;
            }
        }
    }

    void findfol()
    {
        int k,t,p1,o1,chk;
        char *ptr1;
        for(k=0;k<n;k++)
        {
            chk=0;
            for(t=0;t<pro[k].n;t++)
            {
                ptr1=strchr(pro[k].right_of_nonTerm[t],temp);
                if( ptr1 )
                {
                    p1=ptr1-pro[k].right_of_nonTerm[t];
                    if(pro[k].right_of_nonTerm[t][p1+1]>=65 && pro[k].right_of_nonTerm[t][p1+1]<=90)
                    {
                        for(o1=0;o1<n;o1++)
                            if(pro[o1].left_of_non_term[0]==pro[k].right_of_nonTerm[t][p1+1])
                            {
                                    strcat(pro[i].fol,pro[o1].first);
                                    chk++;
                            }
                    }
                    else if(pro[k].right_of_nonTerm[t][p1+1]=='\0')
                    {
                        temp=pro[k].left_of_non_term[0];
                        if(pro[l].right_of_nonTerm[j][p]==temp)
                            continue;
                        if(temp=='S')
                            strcat(pro[i].fol,"$");
                        findfol();
                        chk++;
                    }
                    else
                    {
                        pro[i].fol[strlen(pro[i].fol)]=pro[k].right_of_nonTerm[t] 
   [p1+1];
                        chk++;
                    }
                }
            }
            if(chk>0)
                break;
        }
    }

还要创建一个名为lab6.txt的文本文件。并在下面放置语法

    S ABCDE 
    A a|0
    B b|0
    C c
    D d|0
    E e|0

非终端后面的空格表示->此符号,0表示epsilon。