• 締切済み

線形探索と二分探索

線形探索と二分探索のプログラムを作成中です。 自力(本やwebに落ちているサンプルを参考にして)でここまで作りましたが正直自信がありません。どうかお願いします。 #include <stdio.h> #define ARRAYI1_MAX sizeof(array1) #define ARRAYI2_MAX sizeof(array2) //int binary_search(int*,int,int); //二分探索関数のプロトタイプ宣言 int liner_search(int*,int,int); //線形探索関数のプロトタイプ宣言 void main(void) { int array1[]={2,3,5,8,12,20,32,52}; int array2[]={22,34,65,66,12,33,43,5,1}; int result,key; printf("探す文字を入力して下さい。\n"); sacnf("%d",&key); result=liner_search(array1,ARRAYI1_MAX,key); if(result<0){ printf("見つかりませんでした\n");} else{ printf("%d番目に見つかりました\n",result);} } //線形探索 int liner_search(int*array,int num_array,int key) { int i=0; for(i=0;i<result;i++) } /*二分探索 int binary_search(int*array,int num_array,int key) { }*/

みんなの回答

  • BLUEPIXY
  • ベストアンサー率50% (3003/5914)
回答No.2

バイナリサーチって、ソートされていない配列には適用できませんよ。 array1がキーでarray2がデータという意味ならいいんですけど、array1とarray2のサイズが違いますね。 リニアサーチでは、配列を先頭から最後まで全部探せばいいので、悩むようなことはないですね。 だから、 for(i=0;i<result;i++)というより for(i=0;i<ARRAYI1_MAX;i++)でいいのでは バイナリサーチは、真ん中の値を引っ張り出してその大きさで真ん中より前か後かを決めて、次の部分の真ん中をまた探せばいいです。 ガンバレo(^-^)o

  • Traja
  • ベストアンサー率19% (107/546)
回答No.1

>ここまで作りました って、本質的な部分は全く手が着いていない状態では? int i=0; ・・・・・(1) for(i=0;i<result;i++)・・(2) (2)のfor文で、i=0として初期化するので、(1)で値を初期化する必要なし (2)のresultは、どこで宣言してますか?値は?

kouhei1015
質問者

補足

#include <stdio.h> #define ARRAYI1_MAX sizeof(array1) #define ARRAYI2_MAX sizeof(array2) int binary_search(int*,int,int); //二分探索関数のプロトタイプ宣言 int liner_search(int*,int,int); //線形探索関数のプロトタイプ宣言 void main(void) { int array1[]={2,3,5,8,12,20,32,52}; int array2[]={22,34,65,66,12,33,43,5,1}; int result;//ここでresultを宣言していますが、グローバル関数の方が良いのでしょうか? int key; printf("探す文字を入力して下さい。\n"); sacnf("%d",&key); result=liner_search(array1,ARRAYI1_MAX,key); if(result<0){ printf("見つかりませんでした\n");} else{ printf("%d番目に見つかりました\n",result);} } //線形探索 int liner_search(int*array,int num_array,int key) { int i; for(i=0;i<result;i++) } //二分探索 int binary_search(int*array,int num_array,int key) { }

関連するQ&A

  • 線形探索について

    C言語の線形探索の課題なんですが 5つの整数を入力して その入力した値からみつけたい値を探索する課題なのですが #include <stdio.h> /*--- 要素数nの配列aからkeyと一致する要素を線形探索 ---*/ int search(const int a[], int n, int key) { int i = 0; while (1) { if (i == n) return (-1); /* 探索失敗 */ if (a[i] == key) return (i); /* 探索成功 */ i++; } } int main(void) { int i, ky, idx; int x[4]; int nx = sizeof(x) / sizeof(x[0]); printf("%d個の整数を入力してください。\n", nx); for (i = 0; i < nx; i++) { printf("x[%d]:", i); scanf("%d", &x[i]); } printf("探す値:"); scanf("%d", &ky); idx = search(x, nx, ky); /* 配列xから値がkyである要素を線形探索 */ if (idx == -1) puts("探索に失敗しました。"); else printf("%dは%d番目にあります。\n", ky, idx + 1); return (0); } ここまではわかるのですが、 x[0]=99 x[1]=99 x[2]=88 x[3]=99 x[4]=22 と入力したときに 99は 1番目に見つかりました 2番目に見つかりました 4番目に見つかりました と出力したいのですがうまくいきません 線形探索で同じ数値を探索するにはどうすればよいのですか?

  • 線形探索(番兵法)のプログラムについて。

    線形探索(番兵法)のプログラムについて考えています。 メイン関数からsearch関数に値を渡してそこで探索させるのですが、 int search(int a[], int n, int key) { int i = 0; a[n] = key; while (1) { if (a[i] == key) break; i++; } return (i == n ? -1 : i); } のwhileを使ったやり方からfor文を使ったやり方に変更したいと思っています。 色々な方法でプログラムを考えてみたいので。 そうすると、なんかうまくいきません。 for文だとどのように考えたらいいのでしょうか?

  • 線形探索のエラーがでて困っています

    線形探索を用いて表を作るプログラムを作ったのですが、データの数が10000ならば作動するのですが、それ以上になってしまうとセグメントエラーが起こります。なぜだが教えていただけないでしょうか? #include <stdio.h> #include <stdlib.h> #include <time.h> #define N 1000000 #define M 10 typedef int Key; typedef struct item{ Key key; }Item; struct table { int n; Item item[N]; }; typedef struct table *Table; Item *lookup_item(Table table ,Key key){ int i=0; while(1){ if(i==table->n) return (0); if(table->item[i].key==key) return &(table->item[i]); i++; } return 0; } int add_item(Table table, Item item){ int i; int n=table->n; if(lookup_item(table ,item.key)!=0) return (0); else { table->item[n].key=item.key; table->n++; return (1); } } Table new_table(){ Table table; table = (Table)malloc(sizeof(table)); return table; } int remove_item(Table table, Key key){ int i=0; int n=table->n; if(lookup_item(table,key)!=0) { while(1){ if(table->item[i].key==key){ table->item[i].key=table->item[n-1].key; table->n--; return 1; } i++; } } else return (0); } Key keys[N]; int main() { Table table; Item item; clock_t t1, t2; char buff[128]; int i, j, n; /* ファイルからキーを読み込み keys[] に格納する。*/ for (n=0; n<N && fgets(buff, 128, stdin)!=NULL; n++) { keys[n] = atoi(buff); } /* 表を用意する。*/ table = new_table(); /* 追加項目数と全項目の追加に必要な時間(秒単位)を印字する。*/ t1 = clock(); for (i=j=0; i<n; i++) { item.key = keys[i]; j += add_item(table, item); } t2 = clock(); printf("%d %.3f\n", j, (double)(t2-t1)/CLOCKS_PER_SEC); /* 探索成功数と全項目の探索に必要な時間(秒単位)を印字する。*/ t1 = clock(); for (i=j=0; i<n; i++) { if (lookup_item(table, keys[i])!=NULL) j++; } t2 = clock(); printf("%d %.3f\n", j, (double)(t2-t1)/CLOCKS_PER_SEC); /* 削除項目数と全項目の削除に必要な時間(秒単位)を印字する。*/ t1 = clock(); for (i=j=0; i<n; i++) { j += remove_item(table, keys[i]); } t2 = clock(); printf("%d %.3f\n", j, (double)(t2-t1)/CLOCKS_PER_SEC); return 0; } よろしくお願いします。

  • このプログラムの説明合っていますか?

    /* 線形探索(for文で実現)*/ #include <stdio.h> /*--- 要素数nの配列aからkeyと一致する要素を線形探索 ---*/ int search(const int a[], int n, int key)    { int i;            /*iを宣言*/ for (i = 0; i < n; i++)     /*iの値を設定し宣言*/ if (a[i] == key)       /*iにkeyで入力*/ return (i); /* 探索成功 */ return (-1); /* 探索失敗 */ } int main(void)          /*main関数*/ { int i, ky, idx;/*i,ky,idxを宣言*/ int x[7]; /*xは配列で7つの数字を入れられる*/ int nx = sizeof(x) / sizeof(x[0]);/*配列を宣言*/ printf("%d個の整数を入力してください。\n", nx); for (i = 0; i < nx; i++) { printf("x[%d]:", i); scanf("%d", &x[i]); }printf("探す値:"); scanf("%d", &ky); idx = search(x, nx, ky); /* 配列xから値がkyである要素を線形探索 */ if (idx == -1) puts("探索に失敗しました。"); else printf("%dは%d番目にあります。\n", ky, idx + 1); return (0);      /*0の数字で戻る*/ } 1行ずつ理解したいのですが分からない個所多いんです。 分からないの文は説明が書いてないので教えてください。

  • C言語の二分探索法について質問です。

    C言語の2分探索法について質問です。 以下のようなプログラムを作りたいのですが,途中でよく分からなくなってしまいました。添削お願いします。 入力された整数を配列に順次格納する(必ず昇順になるように入力)。0が入力された時に整数の入力を終了し, 次に入力された数字を二分探索によって配列から探索し,その配列の添字番号を出力するプログラムを作成せよ。 実行例 (例1) (例2) 9 ←入力 1 ←入力 7 ←入力 42 ←入力 69 ←入力 99 ←入力 31 ←入力 13 ←入力 93 ←入力 0 ←入力 59 ←入力 5 ←入力 17 ←入力 not found ←出力 0 ←入力 7 ←入力 2 ←出力 プログラム #include <stdio.h> #include <stdlib.h> #define ARRAY_SIZE 10 int swap(int a, int b) { int c; c = a; a = b; b = a; } int main(void) { int array[] ; int low = 0; int high = n - 1; int mid; int key; int i, j, n; int data; struct node *p; puts("整数を入力して下さい。"); for(i = 0; i < ARRAY_SIZE && scanf("%d", array + i) == 1; ++i){ if(array[i] == 0) break; for(j = i; j > 0 && array[j-1] > array[j]; j--) swap(array[j-1], array[j]); } n = i; puts( "探索する値を入力して下さい" ); scanf( "%d", &key ); while( low <= high ) / { mid = (low + high) / 2; if( array[mid] == key ) { return ; } else if( array[mid] < key ) { low = mid + 1; } else { high = mid - 1; } } puts( "not found" ); return 0; }

  • ソートの名称について

    以下のようなソートに、選択ソートやバブルソート等といった名称は存在しますか? #include <stdio.h> int main(void) { int array[10]; int i, j, tmp; /* Input */ for(i=0; i<sizeof(array)/sizeof(int); i++){ printf("array[%d]> ", i); scanf("%d", &array[i]); } /* Sort */ for(i=0; i<sizeof(array)/sizeof(int)-1; i++){ for(j=i+1; j<sizeof(array)/sizeof(int); j++){ if(array[i]>array[j]){ tmp = array[i]; array[i] = array[j]; array[j] = tmp; } } } /* Output */ for(i=0; i<sizeof(array)/sizeof(int); i++){ printf("array[%d]: %d\n", i, array[i]); } return 0; }

  • ポインタのエラー?

    配列とポインタを使って多数桁の加算をするプログラムを作ったのですが、演算結果を表示した後にエラーが出てしまいます。初心者なので書式もばらばらで読みにくいと思いますが、お願いします。 #include <stdio.h> #include <stdlib.h> #define N 10 void main() { int *a,*b,*result,carry,i; a=(int *)calloc(N+1,sizeof(int)); b=(int *)calloc(N+1,sizeof(int)); result=(int *)calloc(N+1,sizeof(int)); /*配列aへの読み込み*/ for(i=1;i<N+1;i++) scanf("%d",&*(a+i)); *a=0; printf("入力された数値:"); for(i=1;i<N+1;i++) printf("%d",*(a+i)); printf("\n"); /*配列bへの読み込み*/ for(i=1;i<N+1;i++) scanf("%d",&*(b+i)); *b=0; printf("入力された数値:"); for(i=1;i<N+1;i++) printf("%d",*(b+i)); printf("\n"); /*配列resultの初期化*/ for(i=0;i<N+1;i++) *(result+i)=0; carry=0; /*result=a+bの演算*/ for(i=(N+1);i>=0;i--){ *(result+i)=*(a+i)+*(b+i)+carry; if(*(result+i)>=10){ *(result+i)-=10; carry=1; } else carry=0; } /*演算結果の表示*/ printf("和:"); for(i=0;i<N+1;i++) printf("%d",*(result+i)); printf("\n"); /*メモリ領域の解放*/ free(a); free(b); free(result); }

  • ポインタと配列

    次のソースで、結果表示でポインタを使いたいのですが、うまくいきません。1件しか表示されないのです。 ポインタの扱いがおかしいのだと思いますが、どうしたらよいでしょうか? #include <stdio.h> #include <string.h> int search(char key[256],FILE *fp,char *result[256][256]); main(void) { FILE *fp; int rep,n,i; char x[256],key[256],*result[256][256]; printf("検索キーワードを入力してください。\n" "キーワード>"); gets(key); if((fp=fopen("personal.txt","r"))==NULL) { printf("ファイルをオープンできません\n"); exit(1); } printf("=====検索結果=====\n"); n=search(key,fp,result); for(i=0;i<n;i++) { printf("%s\n",result[i]); } printf("検索結果:%d件です。\n",n); fclose(fp); } int search(char key[256],FILE *fp,char *result[256][256]) { int n=0; char *p,word[256],*name; while((p=fgets(word,256,fp))!=NULL) { if(strstr(word,key)!=NULL) { name=strtok(p," "); strcpy(result[n],name); n++; } } return n; } 実行すると、下の警告がでます。 illegal pointer combination(param)

  • なぜエラーになるのでしょう。

    #include <stdio.h> #include <stdlib.h> #include <string.h> #define STR_MAX 512 #define LINE_MAX 30000 int main(void){ // ※↓がエラー原因※ char str[LINE_MAX][STR_MAX]; printf("%d\n", sizeof(int)); printf("%d\n", sizeof(int[10])); printf("%d\n", sizeof(char[10])); printf("%d\n", sizeof(char[STR_MAX])); printf("%d\n", sizeof(char[LINE_MAX])); printf("%d\n", sizeof(char[LINE_MAX][STR_MAX])); printf("%d\n", sizeof(long[STR_MAX][LINE_MAX])); printf("%d\n", sizeof(str)); return 1; } というプログラムを実行すると「問題が発生したため~を終了します。ご不便をかけて~」という問題が発生して終了してしまいます。 原因は、 printf("%d\n", sizeof(str)); の部分であるのですが、 char str[LINE_MAX][STR_MAX]; という宣言でメモリ使用量が大きすぎるということでしょうか? しかし、 printf("%d\n", sizeof(char[LINE_MAX][STR_MAX])); printf("%d\n", sizeof(long[STR_MAX][LINE_MAX])); でも正常に実行できているのに・・・ もともとは、何万行もあるテキストファイルを配列に一度格納し、それらを編集して出力しようと思っていたのですが、毎回エラーが発生するので、調べたところ配列宣言の部分 char str[LINE_MAX][STR_MAX]; にエラーがあるということが分かったのですが、原因が分かっても理由がさっぱり分かりません。 googleで配列の上限について調べたり、仕様について調べたのですが、ほしい回答が得られず質問させてもらいました。 分かる方いましたら教えてください。 ちなみにExcelのマクロを組んだときにdim StrTemp(512, 30000) as stringと宣言して Option Explicit Function SampleTest() Dim StrTemp(512, 30000) As String Dim i, j As Integer For i = 1 To 512 For j = 1 To 30000 StrTemp(i, j) = "SampleTest" Next j Next i End Function と処理をすることはできたので、パソコンのメモリ容量が足りないとは思えないのです。

  • sizeof

    main() { char array1[256] = "abcdefg"; char *array2 = "stuvwxyz"; printf("array1 = %d\n",sizeof(array1)); // array1 = 256 printf("array1 = %d\n",sizeof(array1)/sizeof(char)); // array1 = 256 printf("array2 = %d\n",sizeof(array2)); // array2 = 4 printf("array2 = %d\n",sizeof(array2)/sizeof(char *)); // array1 = 1 printf("array2 = %d\n",sizeof(*array2)); // array2 = 1 } となるのですが、sizeof(array1)では、配列のサイズが取得できるのですが、array2がさす配列のサイズを得るためにはどうすればいいのですが?もしくは取得デキナイのはなぜでしょうか。 それと、 sizeof(array2)では、charへのポインタをさすから4バイト。 sizeof(*array2)では、sizeof(array[0])を意味するから1バイト という解釈でいいでしょうか。

専門家に質問してみよう