C言語・スタックを使用した逆ポーランド記法について

このQ&Aのポイント
  • C言語でスタック(リスト構造)を使用した逆ポーランド記法のプログラムを作りたいのですが、どのようにして数字と演算子を区別すればいいのでしょうか?
  • 質問者はC言語でスタックを使用した逆ポーランド記法のプログラムを作成したいと考えています。具体的には、計算式(例:1234+*+)が入力されたとき、数字と演算子をどのように区別するかを知りたいとしています。
  • プログラムの一部として、スタック構造の定義や操作のコードが提示されています。
回答を見る
  • ベストアンサー

C言語・スタックを使用した逆ポーランド記法について

C言語でスタック(リスト構造)を使用した逆ポーランド記法のプログラムを作りたいのですが 計算式(例:1234+*+)が入力された場合、どのようにして数字と演算子を区別すればいいのでしょうか? 一応スタック構造の部分は、 #include <stdio.h> #include <stdlib.h> /*スタック構造*/ typedef struct stack { int max; int ptr; int *stk; } Stack; /*スタックの確保・初期化*/ int StackAlloc(Stack *s, int max) { s->ptr = 0; if ((s->stk = calloc(max, sizeof(int))) == NULL) { s->max = 0; return (-1); } s->max = max; return (0); } /*スタック解放*/ void StackFree(Stack *s) { if (s->stk != NULL) { free(s->stk); s->max = s->ptr = 0; } } /*プッシュ*/ int StackPush(Stack *s, int x) { if (s->ptr >= s->max) return (-1); s->stk[s->ptr++] = x; return (0); } /*ポップ*/ int StackPop(Stack *s, int *x) { if (s->ptr <= 0) return (-1); *x = s->stk[--s->ptr]; return (0); } /*データのピーク*/ int StackPeek(const Stack *s, int *x) { if (s->ptr <= 0) return (-1); *x = s->stk[s->ptr - 1]; return (0); } /*スタックの大きさを返却*/ int StackSize(const Stack *s) { return (s->max); } /*データを返却*/ int StackNo(const Stack *s) { return (s->ptr); } /*スタックは空か*/ int StackEmpty(const Stack *s) { return (s->ptr <= 0); } /*スタックは満杯か*/ int StackFull(const Stack *s) { return (s->ptr >= s->max); } /*スタックを空にする*/ void StackClear(Stack *s) { s->ptr = 0; } といった感じで仕上げています。

  • BNR33
  • お礼率14% (5/34)

質問者が選んだベストアンサー

  • ベストアンサー
  • jjk65536
  • ベストアンサー率59% (66/111)
回答No.4

つい2週間くらい前に逆ポーランドの処理コードを書きました。 言語はObjective-Cでしたけど。 記憶に新しいので助言します。 まず、逆ポーランドの処理では、数値も演算子もトークン(呼び方は一例)として 扱います。 C言語でしたら、トークンを構造体で表現するのが自然かと思います。 typedef enum {   TOKEN_TYPE_NUM,   TOKEN_TYPE_OPERAND } token_type; typedef struct {   token_type type;   int value; // 数値または演算子 } token; そうすると、トークンは1234+*+の7つあるわけですから、tokenポインタが7つPushされた スタックを作ります。 あとはルールに従ってPopとPushで処理していけばいいですよね。 > どのようにして数字と演算子を区別すればいいのでしょうか? もうお分かりかと思いますが、一例を書きます。 token *t; StackPop(s, &t); if(t->type == TOKEN_TYPE_NUM){   // t->valueを数値として処理 } if(t->type == TOKEN_TYPE_OPERAND){   // (char)t->valueを演算子として処理 } 最後に、ほかの方も指摘していますが、質問者様のコードはツリー型のスタックになっていません。 というか、スタック実装は通常リンクリストであってツリーにはしないです。 ツリーを使う処理として、二分探索木なんかが教科書にはよく登場します。 http://ja.wikipedia.org/wiki/2%E5%88%86%E6%8E%A2%E7%B4%A2%E6%9C%A8 スタックでは、通常ノードとノードがポインタで連結した構造をとります。 具体的にはこんなコードになるはずです。 http://www.freecprograms.com/lilink.htm 勉強用であればそのままでもいいかもしれませんが、とりあえずポインタのPush/Popが できるように改造しないとjjk65536案は使えないですね。

その他の回答 (4)

  • jjk65536
  • ベストアンサー率59% (66/111)
回答No.5

No.4です。 ツリーなんてどこにも書いてないですね。 大変失礼しました。 お恥ずかしい。

  • LOHA
  • ベストアンサー率52% (203/388)
回答No.3

>どのようにして数字と演算子を区別すればいいのでしょうか? 入力が文字列であると仮定した場合ですが、一文字目から順に見ていって、普通にswitchかifで比較・処理するのではダメなのでしょうか? たとえば、 char* input = "1234+*+"; ならforつかって if (input[i] >= '0' && input[i] <= '9') { 数値の処理 } else if (input[i] == '*') { 掛け算の処理 } (以下略) あるいは switch (input[i]) {  case '0': case'1': ... case'9': 数値の処理  case '*': 掛け算の処理  (以下略) } という感じで比べられます。

  • asuncion
  • ベストアンサー率33% (2126/6286)
回答No.2

>スタック(リスト構造)を使用した と書いてありますが、構造体が自己参照型になってませんね。 リスト構造を使ったことになってないんじゃないですか?

  • Tacosan
  • ベストアンサー率23% (3656/15482)
回答No.1

その例の「1234+*+」は何を意味するのですか?

関連するQ&A

  • プログラムについて

    今スタっクのファイルから読み込んだ文字列をスタっクへプっシュしたりポっプしたりする過程がわかるプログラムを作ってます 。 作りかけのプログラムですがどこをどうすればいいか教えてください!! 一応コンパイルできます。 使ってない関数があるかもしれません。 #include <stdio.h> #include <stdlib.h> #include <string.h> #define NUMBER 100 /*--- スタックを実現する構造体 ---*/ typedef struct { int max; /* スタックのサイズ */ int ptr; /* スタックポインタ */ char *stk; /* スタック(の先頭要素へのポインタ) */ } Stack; /*--- スタックの初期化 ---*/ int StackAlloc(Stack *s, int max) { s->ptr = 0; if ((s->stk = calloc(max, sizeof(int))) == NULL) { s->max = 0; /* 配列の確保に失敗 */ return (-1); } s->max = max; return (0); } /*--- スタックの後始末 ---*/ void StackFree(Stack *s) { if (s->stk != NULL) { free(s->stk); s->max = s->ptr = 0; } } /*--- スタックにデータをプッシュ ---*/ int StackPush(Stack *s, int x, int i,char *a[]) { if (s->ptr >= s->max) return (-1); if(x>=i) { puts("プッシュできる文字データはありません。"); return (-1); } strcpy(&s->stk[s->ptr++],&(*a)[x]); x++; return x; } /*--- スタックからデータをポップ ---*/ int StackPop(Stack *s, int x,char *a[]) { if (s->ptr <= 0) /* スタックは空 */ return (-1); strcpy(&s->stk[--s->ptr],&(*a)[x]); return (0); } /*--- スタックからデータをピーク ---*/ int StackPeek(const Stack *s, int *x) { if (s->ptr <= 0) /* スタックは空 */ return (-1); *x = s->stk[s->ptr - 1]; return (0); } /*--- スタックの大きさ ---*/ int StackSize(const Stack *s) { return (s->max); } /*--- スタックに積まれているデータ数 ---*/ int StackNo(const Stack *s) { return (s->ptr); } /*--- スタックは空か ---*/ int StackIsEmpty(const Stack *s) { return (s->ptr <= 0); } /*--- スタックは満杯か ---*/ int StackIsFull(const Stack *s) { return (s->ptr >= s->max); } /*--- スタックを空にする ---*/ void StackClear(Stack *s) { s->ptr = 0; } int main(void) { int i=0,j,ret,x=0; char *a[NUMBER]; char buffer[20]; FILE *fpin; Stack s; fpin=fopen("input2.txt","r"); //テキストファイルを読み取りモードで開く while(fgets(&buffer[0],sizeof(buffer),fpin) !=NULL ) { if(i>=NUMBER)//読み込む人数がNUMBERを超えてる時の処理 { puts("人数が100人を超えています"); goto END; } strcpy(&a[i][0],&buffer[0]); /*ret=sscanf(&buffer[0],"%s",&a[i][0]); //データ文字列を3分割 if(ret!=1) //1に分割できなかったときの処理 { puts("代入された入力項目の個数が3でありません"); goto END; }*/ i++; } for(j=0; j<i; j++) printf("%s\n",&(*a)[j]); if (StackAlloc(&s, 100) == -1) { puts("スタックの確保に失敗しました。"); return (1); } while (1) { int m; printf("現在のデータ数:%d/%d\n", StackNo(&s), StackSize(&s)); printf("(1) プッシュ (2) ポップ (0) 終了:"); scanf("%d", &m); if (m == 0) break; switch (m) { case 1: printf("データ:"); puts("こんちくしょ~"); if(StackPush(&s, x,i,&(*a)) == -1) puts("スタックへのプッシュに失敗しました。"); break; case 2: if(StackPop(&s, x,&(*a)) == -1) puts("ポップできません。"); else printf("ポップしたデータは%sです。\n", &s.stk[s.ptr]); break; } } StackFree(&s); END: fclose(fpin); return (0); }

  • c言語 スタックの標準入力の課題です

    c言語のスタックについての質問です。 実装したのですが、標準入力の部分を i 9 o i 8 i 7 o i 6 i 5 o i 4 o o i 3 i 2 i 1 o o e といったように指示を一括してやるために直す方法を教えていただきたいです。 iはプッシュ oはポップ eは終了 sは入力時点でのスタックに格納された全体の内容表示 となってます。 #include<stdio.h> #define MaxSize 100 //スタックサイズ int stack[MaxSize];//スタック int sp;//スタックポインタ int push(int); int pop(int *); void show_stack(); void main(void) { int c,n; while(printf("]"),(c=getchar())!=EOF){ rewind(stdin); if(c=='i'||c=='I'){ printf("data--> "); scanf("%d", &n); rewind(stdin); if(push(n)==-1){ printf("スタックがいっぱいです\n"); } } if(c=='o'||c=='O'){ if(pop(&n)==-1) printf("スタックは空です\n"); else printf("stack data-->%d\n",n); if(c=='e'||c=='E') break; } if(c=='s'||c=='S') show_stack(); } } int push(int n)//スタックにデータをつむプッシュ { if(sp<MaxSize){ ++sp; stack[sp]=n; return 0; } else return -1; } int pop(int *n) { if(sp>0){ *n=stack[sp]; sp--; return 0; } else return -1; } void show_stack() { int i; puts("スタックの内容"); if(sp<0){ printf("スタックは空です。\n"); } else for(i=sp;i>=1;i--) { printf("%11d\n",stack[i]); printf("\n"); } }

  • C言語のソースの説明なんですが

    #include <stdio.h> #define MAX 256 void pushdown(char *S, char x); char popup(char *S); void initialize(char *S); int empty(char *S); int top=0; void pushdown(char *S, char x){ /*スタックSにデータxを記憶*/ if(top<MAX){ top++; S[top]=x; } else{ printf("Stack S overflows.\n"); } } char popup(char *S){ /*スタックSからデータの取出し*/ if(top>0){ top--; return(S[top+1]); } else{ printf("Stack S is empty.\n"); return('\0'); } } void initialize(char *S){ int i; top=0; for(i=1;i<MAX;i++){ S[i]='\0'; } } int empty(char *S){ if(top==0){ return(1); } return(0); } int main(void){ char x; char S[MAX]; pushdown(S,'a'); pushdown(S,'b'); pushdown(S,'c'); x=popup(S); x=popup(S); pushdown(S,'d'); x=popup(S); pushdown(S,'e'); while(!empty(S)){ printf("%c", popup(S)); } printf("\n"); return(0); } 上記のソースリストに説明を載せなくてはいけないのですがどれが何をしているのかほとんど分からなくて困っています。(わかったのは既に書いてある2行分ぐらい) 長くて面倒ですが判る方、どうか助けてください。 (インデント等は省いています)

  • C言語で変更していただきたい所があるのですが・・・

    下のソースを加減乗除だけでなく、余りを求める演算(%)やべき乗演算(^)も使えるようにしたいのですがうまくいきません。 どなたか変更例をお見せできますでしょうか? #include <stdio.h> #include <stdlib.h> #define STACK_MAX 10 /* 配列によるスタック構造 */ double stack[STACK_MAX]; /* スタック頂上の位置(最下部からのオフセット)*/ int stack_top = 0; /* スタックへのpush */ void stack_push(double val) { if(stack_top == STACK_MAX) { /* スタックが満杯になっている */ printf("エラー:スタックが満杯です(Stack overflow)\n"); exit(EXIT_FAILURE); } else { /* 渡された値をスタックに積む */ stack[stack_top] = val; stack_top++; } } /* スタックからpop */ double stack_pop(void) { if(stack_top == 0) { /* スタックには何もない */ printf("エラー:スタックが空なのにpopが呼ばれました" "(Stack underflow)\n"); exit(EXIT_FAILURE); return 0; } else { /* いちばん上の値を返す */ stack_top--; return stack[stack_top]; } } int main(void) { char buffer[256]; double cal1, cal2; int i; do { printf("現在のスタック(%d個):", stack_top); for(i = 0; i < stack_top; i++) { printf("%0.3f ", stack[i]); } printf("\n>"); fgets(buffer, 255, stdin); switch(buffer[0]) { case '+': cal1 = stack_pop(); cal2 = stack_pop(); stack_push(cal2 + cal1); break; case '-': cal1 = stack_pop(); cal2 = stack_pop(); stack_push(cal2 - cal1); break; case '*': cal1 = stack_pop(); cal2 = stack_pop(); stack_push(cal2 * cal1); break; case '/': cal1 = stack_pop(); cal2 = stack_pop(); stack_push(cal2 / cal1); break; case '=': /* =の場合はこのすぐあとでwhile文からも抜ける */ break; default: /* 入力された値は数字のはずなので,スタックに積む */ stack_push(atoi(buffer)); break; } } while(buffer[0] != '='); printf("計算結果は%f です。\n",stack_pop()); if(stack_top != 0) { printf("エラー:スタックにまだ数が残っています\n"); return EXIT_FAILURE; } return EXIT_SUCCESS; }

  • スタックについて

    スタックを実現するプログラムを作っているのですが、実行するとセグメテーション違反が表示されます。でもどこが間違っているのかわかりません!どうしたらいいのでしょう? #include<stdio.h> #include<stdlib.h> struct stack{ int max; int used; int *array; }; struct stack * stack_create(int n) { struct stack *s; int i; s->array=(int *)malloc(sizeof(int)*n); s->used=0; s->max=n; return 0; } void stack_free(struct stack *s) { free(s); } int stack_push(struct stack *s,int datum) { if(s->used>=s->max){ return 0; } s->array[s->used]=datum; s->used++; return 1; } int stack_pop(struct stack *s,int *datump) { if(s->used<=0){ return 0; } *datump=s->array[s->used-1]; s->used--; return 1; } int stack_is_empty(const struct stack *s) { return s->used==0; } int main() { struct stack s; int i,p; int n; scanf("%d",&n); stack_create(n); for(i=0;i<=5;i++){ stack_push(&s,i); printf("push%2d\n",i); } for(i=1;i<=3;i++){ stack_pop(&s,&p); printf("pop%2d\n",p); } }

  • ソートを自作

    一方向リストを使ってデータを記憶するプログラムに、ソート機能を持つ関数自作する。 機能は<名前:辞書順、数字:小さい順>に並び替える。 このとき以下のアルゴリズムしたがって作ります。 『与えられたリストをリストA、ソート済みのリストをリストBと呼ぶことにする。処理の開始段階では、リストBは空である。 1: リストAの要素の中で、最大値をもつ要素Cを探す。 2: 要素CをリストAから削除する。 3: 要素CをリストBの先頭に挿入する。 4: リストAが空であれば終了。空でなければ Step1 にもどる。 』 下のコードは自分で考えてみたものです。全部は長いので構造体、関数のみ載せます。 typedef struct member{ char name[40]; int number; struct member *next; } MEMBER; int compar_name(const MEMBER *x, const MEMBER *y){ return strcmp(x->name, y->name); } int compar_number(const MEMBER *x, const MEMBER *y){ return (x->number - y->number); } void remove_max(MEMBER *list, MEMBER *max, int(*compar)(const void*, const void*)){ /* 最大値maxをlistから削除 */ MEMBER *p, *q; p=list->next; q=list; if(p==NULL && compar(q,max)==0) { return; } else if(compar(q,max)==0) { q=p; } else{ while(compar(p,max)!=0) { q=p; p=p->next; } q->next=p->next; free(p); }} MEMBER *find_max(MEMBER *list, int(*compar)(const void*, const void*)){ /* 最大値maxを探す */ MEMBER *ptr, *max; for (ptr=max=list; ptr!=NULL; ptr=ptr->next){ if (compar(max,ptr)<0){ max=ptr; } } return max; } MEMBER *listsort(MEMBER *list, int(*compar)(const void*, const void*)){ /* ソート関数 */ MEMBER *sorted, *ret; ret=list; for (;ret->next; ret=ret->next){ MEMBER *tmp, *max=NULL; max=find_max(list, (int(*)(const void*, const void*))compar); remove_max(list, max, (int(*)(const void*, const void*))compar); sorted=(MEMBER *)malloc(sizeof(MEMBER)); strcpy(sorted->name, max->name); sorted->number=max->number; sorted=tmp; tmp=sorted; } return sorted; } 並べ替えるデータの例: OKITA 1 HARADA 10 TOUDOU 8 INOUE 6 SAITOU 3 NAGAKURA 2 TAKEDA 5 TANI 7 MATUBARA 4 SUZUKI 9 長いですが、教えて下さい。<(_ _)>

  • C言語の関数に関する質問ですが

    C言語の初心者です。よろしくお願いいたします。 授業でこのような演習が出ました。 演習:実数x を入力したときの最大値を求めるプログラムを作れ. 実数x を入力すると,x; -x; x2; xの絶対値の平方根 の中で一番大きい値を答える プログラムを作れ(ファイル名はmax.c とする). 表示は以下のようにする. Input x: -0.5 【Enter】 Answer is 0.707107. #include<stdio.h> #include<math.h> double max(double a, double b){ if( a > b) return a; else return b; } int main(void) { double x,y; printf(\"Input x: \"); scanf(\"%lf\",&x); y = max (x,-x); y = max (y,x*x); y = max (y,sqrt(fabs(x))); printf(\"Answer is %f.\\n\",y); } このように書けばうまく実行できますが、関数の中に関数を使えないでしょうか。うまく言えないですが、たとえば、以下のように書いてみましたが、うまく実行できません。どう直したらいいでしょうか、お忙しい中教えていただけたらうれしいです。 #include <stdio.h> #include <math.h> int max(double a,double b) { if (a<b) return b; else return a;} int main(void) { double x,result; printf(\"Input x:\"); scanf(\"%lf\",&x); result=max(max(x,-x),max(pow(x,2),sqrt(fabs(x)))); printf(\"%.2f\",result); return 0; } よろしくお願いいたします!!

  • C言語の質問です!

    #include "stdafx.h" #include <iostream> #include <string> #include <stdio.h> #include <math.h> #include <string.h> #include <stdlib.h> #include <time.h> #include <conio.h> using namespace std; double arrayMin(double array[][], int n){ double Min=9999999999999999999999.999999; for(int N=0;N<n;N++){ if(array[N][0]!=NULL&&array[N][0]<Min){ Min=array[N][0]; } } return Min; } double arrayMax(double array[][], int n){ double Max=-9999999999999999999999.999999; for(int N=0;N<n;N++){ if(array[N][0]!=NULL&&array[N][0]<Max){ Max=array[N][0]; } } return Max; } int main(){ double data[3][10] = {{2.0, 1.0, 5.0, 3.0, 2.0, 21.0, 4.0, 5.0, 4.0, 28.0}, {1.0, 1.0, 5.0, 3.0, 2.0, 21.0, 4.0, 5.0, 4.0, 28.0}, {3.0, 1.0, 5.0, 3.0, 2.0, 21.0, 4.0, 5.0, 4.0, 28.0}}; double min, max; min=arrayMin(data, 3); max=arrayMax(data, 3); printf("min = %lf, max = %lf\n", min, max); return 0; } 二次元配列の1行目の配列の最大値と最小値を求めることを考え,上のようなプログラムを書いたのですが, 1>.\maxmin.cpp(12) : error C2087: 'array' : 添字がありません。 1>.\maxmin.cpp(21) : error C2087: 'array' : 添字がありません。 1>.\maxmin.cpp(34) : error C2059: 構文エラー : ']' 1>.\maxmin.cpp(35) : error C2664: 'arrayMax' : 1 番目の引数を 'double [3][10]' から 'double [][1]' に変換できません。(新しい機能 ; ヘルプを参照) 1> 指示された型は関連がありません。変換には reinterpret_cast、C スタイル キャストまたは関数スタイルのキャストが必要です。 というようなエラーが出てしまいます. 途中のarray[N][0]!=NULLは二次元配列dataが3行より少ない場合に対応させています. どなたかアドバイスをいただけますでしょうか? よろしくお願いいたします!

  • C言語 二分木探索

    今、int型の二分木にデータを追加する関数(引数は二分木へのポインタと追加する値、追加されたノードへのポインタを返す)をつくろうとしてます。 以前リストにデータを追加する関数をつくったのでそれを変更してつくろうとしているのですが途中までいってつまってしまいました。 つくりかたを教えてください。 よろしくお願いします! struct BinaryTreeNode{ int data; struct BinaryTreeNode *l_next; struct BinaryTreeNode *r_next; }; struct BinaryTree{ int node_num; struct BinaryTreeNode *root; }; BinaryTreeNode *BinaryTreeNodeAlloc(void) { BinaryTreeNode *node; node = (BinaryTreeNode *)malloc(sizeof(BinaryTreeNode)); if (node == NULL) { return (NULL); } node->l_next = NULL; node->r_next = NULL; return (node); } BinaryTreeNode *BinaryTreeDataAdd(BinaryTree *list, int x) { BinaryTreeNode *ptr; BinaryTreeNode *prev; BinaryTreeNode *new_node; ptr = list->root; prev = NULL; while (ptr) {       ←?? if (ptr->data < x) { prev = ptr; ptr = ptr->next; } else if (ptr->data == x) { return (NULL); } else { new_node = BinaryTreeNodeAlloc(); if (new_node == NULL) { exit (0);                ←?? } new_node->data = x; new_node->next = ptr; if (prev != NULL) { prev->next = new_node; } else { list->head = new_node; } list->node_num++; return (new_node); } } new_node = BinaryTreeNodeAlloc(); if (new_node == NULL) { exit (0); } new_node->data = x; new_node->r_next = NULL; new_node->l_next = NULL; if (prev != NULL) { prev->next = new_node; } else { list->head = new_node; } list->node_num++; return (new_node); }

  • C言語について

    以下のプログラムについて alice.txtからテキストを読み込みその中の異なる単語の数を求めるプログラムです #include<stdio.h> #include<stdlib.h> #include<string.h> #include<stddef.h> #include<ctype.h> #define NMAX 80 #define LMAX 5000 void count(int); void all_words(void); FILE *fp, *fp2; char *fn="alice.txt"; char *fn2="total word.txt"; const char *ignore="\n !?()*-;:.,_\"[]"; int main(void){ int p=0, x=0, c, l, t=0; char word3[LMAX][NMAX]; char word1[NMAX]; char word2[NMAX]; char *tp; char *tp2; if((fp=fopen(fn,"r"))==NULL){ printf("Can't open '%s'.\n",fn); return -1; } if((fp2=fopen(fn2,"w"))==NULL){ printf("Can't open '%s'.\n",fn2); return -1; } for(c=0;c<LMAX;c++){ if(fgets(word3[c],NMAX,fp)==NULL) break; p++; } for(c=0;c<p;c++){ for(x=0;x<NMAX;x++){ word1[x]=tolower(word3[c][x]); } tp=word1; while((tp2=(char*)strtok(tp,ignore))!=NULL){ if(*tp2=='\''){ if(*(tp2+1)=='`'){ t=1; } tp2++; } strcpy(word2,tp2); l=strlen(word2)-1; if(word2[l]=='\''){ word2[l]='\0'; } if(word2[l]==l){ word2[l]='\0'; } if(word2[0] =='\'' &&t==0){ if(word2[1]!='\0'){ fputs(word2+1,fp2); fputc('\n',fp2); } } else{ if(word2[0]!='\0'){ fputs(word2,fp2); fputc('\n',fp2); } } tp=NULL; } } fclose(fp); fclose(fp2); all_words(); return 0; } void all_words(void){ char word3[NMAX]; int n=0; if((fp2=fopen(fn2,"r"))==NULL){ printf("Can't open '%s'.\n", fn2); return; } for(;;){ if(fgets(word3, NMAX,fp2)==NULL){ break; } n++; } fclose(fp2); count(n); } void count(int n){ int c, x, y=0; char *m=(char *)malloc(n*NMAX); char *xp; char *yp; if((fp2=fopen(fn2,"r"))==NULL){ printf("Can't open '%s'.\n", fn2); free(m); return; } for(c=0,xp=m; c<n;c++,xp+=NMAX){ fgets(xp,NMAX,fp2); } qsort(m,n,NMAX,(int (*)(const void*, const void*))strcmp); c=1; for(x=0,xp=m,yp=m+NMAX;x<n-1;xp+=NMAX,yp+=NMAX,x++){ if(strcmp(xp,yp)==0){ y++; c++; } else{ c=1; } } printf("%d\n",n-y); free(m); fclose(fp2); } このプログラムを実行するとメモリリークになってしまうのですが 確保していないメモリ領域に代入しているのが原因らしいのですが いろいろ試してみたのですがメモリリークが直りません どうしたらよいでしょうか? よろしくお願いします