//■ビットハンドリングによる集合演算 // // 実行時、次のように入力します。 // // (1)集合への追加 // add <要素番号> in <変数名> または add <要素番号> into <変数名> // または add <要素番号> <変数名> // // (2)集合から削除 // del <要素番号> from <変数名> または del <要素番号> in <変数名> // del <要素番号> <変数名> // // (3)集合に入っているかどうかのチェック // check <要素番号> in <変数名> または check <要素番号> <変数名> // // (4)代入 // <左辺の変数名> = <式> // // (5)式 // <変数名> or <変数名> または <変数名> and <変数名> または <変数名> dif <変数名> // // なお、演算子は以下を示す。 // // or : 和集合(Union), and : 積集合(Intersection), dif : 差集合(Difference) // // #include "stdio.h" #include "string.h" #define MAXBIT 128 #define NUMARR (MAXBIT+31)/32 #define MAXSET 100 typedef struct{ char name[32]; unsigned long DT[NUMARR]; }setData; setData dt[MAXSET+1]; int numdt=0; unsigned long bitP(int N, int *i){ unsigned long MB=1; while(N>=32){ N-=32; (*i)++;} return MB << N; } void addSet(unsigned long DT[], int N){ if(N=MAXBIT) return 0; int i=0; return DT[i] &= bitP(N, & i); } void orSet(unsigned long A[],unsigned long B[],unsigned long C[]){ //int N=(MAXBIT+31)/32; for(int i=0;i=MAXSET) { printf("*** error overflow!"); return -1; } for(int j=0;j>=1){ if((j%8)==0) printf(" "); printf("%d",D&1); } } printf("\n\n"); } static unsigned curC; int getToken(char S[]){ int i=0; //unsigned char C=getchar(); while(curC !=0x1A && curC<=0x20) curC=getchar(); if(curC==0x1A) return EOF; if(curC == '=') { S[i++]='=';S[i]=0; curC=getchar();return 0; } for(i=0; curC>0x20 && curC!='='; curC=getchar(), i++) S[i]=curC; S[i++]=0; return 0; } int getNumber(char S1[]){ int a; if(S1[0]>='0' && S1[0]<='9') sscanf(S1,"%d", &a); else {printf("整数を入力して下さい[%s]",S1); a = MAXBIT + 1;} return a; } int main(){ curC=getchar(); char S1[32], S2[32],S3[32], ope[4];int a; while(getToken(S1)!=EOF){ if(strcmp(S1,"add")==0){ if(getToken(S1)==EOF)break; a=getNumber(S1); if(getToken(S1)==EOF)break; if(strcmp(S1,"in")==0 ||strcmp(S1,"into")==0) { if(getToken(S1)==EOF)break; } int id; if((id=searchSet(S1))<0) break; printf("\n name : %s",dt[id].name); addSet(dt[id].DT, a); printSet(dt[id].DT); } else if(strcmp(S1,"del")==0){ if(getToken(S1)==EOF)break; a=getNumber(S1); if(getToken(S1)==EOF)break; if(strcmp(S1,"from")==0 || strcmp(S1,"in")==0) { if(getToken(S1)==EOF)break; } int id; if((id=searchSet(S1))<0) break; printf("\n name : %s",dt[id].name); delSet(dt[id].DT, a); printSet(dt[id].DT); } else if(strcmp(S1,"check")==0){ if(getToken(S1)==EOF)break; a=getNumber(S1); if(getToken(S1)==EOF)break; if(strcmp(S1,"in")==0) { if(getToken(S1)==EOF)break; } int id; if((id=searchSet(S1))<0) break; if(inSet(dt[id].DT, a)) printf(" true"); else printf(" false"); printf("\n"); } else { if(getToken(S2)==EOF)break; if(strcmp(S2,"=")==0) { strcpy(S3,S1); if(getToken(S1)==EOF)break; if(getToken(S2)==EOF)break; if(strcmp(S2,"and")==0 || strcmp(S2,"or")==0 || strcmp(S2,"dif")==0) { strcpy(ope,S2); if(getToken(S2)==EOF)break; } else strcpy(ope,"and"); } else{ strcpy(S3,"$$tmp"); if(strcmp(S2,"and")==0 || strcmp(S2,"or")==0 || strcmp(S2,"dif")==0) { strcpy(ope,S2); if(getToken(S2)==EOF)break; } else strcpy(ope,"and"); } int id1, id2, id3; if((id1=searchSet(S1))<0) break; if((id2=searchSet(S2))<0) break; if((id3=searchSet(S3))<0) break; if (strcmp(ope,"and")==0) andSet(dt[id1].DT, dt[id2].DT, dt[id3].DT); else if(strcmp(ope,"or" )==0) orSet (dt[id1].DT, dt[id2].DT, dt[id3].DT); else difSet(dt[id1].DT, dt[id2].DT, dt[id3].DT); printf("\n name : %s",dt[id3].name); printSet(dt[id3].DT); } } getchar(); return 0; }