• ベストアンサー

データ構造とアルゴリズムの問題が分かりません。

以下の問題で悩んでいます。 1 配列とリストでデータを末尾に追加する場合の時間計算量をO記法で表せ。 2 配列とリスト、それぞれの時間計算量以外の利点と欠点をなるべく多く挙げよ。 3 データ構造「スタック」、「キュー」を配列もしくはリストで実現した場合、それぞれの利点と欠点を挙げよ。 4 アルゴリズム「線形探索」、「二分探索」で特定のデータを検索するための時間計算量をO記法で表し、またその理由も記述せよ。 5 データを検索する操作のほうが多い場合と、データを追加する操作が多い場   合、 「線形探索」と「二分探索」どちらが有利か理由をつけて述べよ。 1は、挿入と削除はO記法で表せたのですが、追加が分かりませんでした。 2は配列の利点はランダムアクセス可能な点と任意のデータをすぐに扱える点の2点 リストの利点は扱うデータを自由に変えられる点の1点しか思いつかず、欠点はよく分かりませんでした。 3、4、5も理由をつけて説明しろと言われたら無理です。 テストに類題を出すと先生はおっしゃってたので、どうしてもすぐに回答が必要です。先生にも質問したのですが、テストに類題を出すから教えられない。自力で頑張れと言われ困っています。 どなたか御助力よろしくお願いいたします。

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

  • ベストアンサー
noname#119918
noname#119918
回答No.3

1 配列とリストでデータを末尾に追加する場合の時間計算量をO記法で表せ。 配列 O(n) リストO(1) 2 配列とリスト、それぞれの時間計算量以外の利点と欠点をなるべく多く挙げよ。 配列は一般にサイズ固定ですが、リストは一般にサイズ可変です。 実装方法にもよりますが、普通配列の方が構造・アルゴリズムが単純ですので、高速でメモリ消費量が少ないです。 リストでは、動的なメモリ管理(malloc/free)を使うことが多いので、 アルゴリズムがやや複雑で、速度・メモリ消費量の点では若干不利かもしれません。 逆にリストのほうが、多様なデータへの対応をしやすく、柔軟性が高いと言えるでしょう。 3 データ構造「スタック」、「キュー」を配列もしくはリストで実現した場合、それぞれの利点と欠点を挙げよ。 双方向リストを用いるのであれば、先頭に対する挿入・削除、末尾に対する挿入・削除は1stepで行えます。 キューの実現にリストを用いれば、キューへの追加・キューからの取り出しは簡単にできます。 キューの実現に配列を用いると、先頭要素を取り出す毎に、配列全要素のシフトが必要になるため、非効率です。 スタックは普通、末尾へのpush,popのみ許可するため、上の問題は生じず、配列でも問題はないと思います。 強いていうならば、配列はサイズ固定ですから、スタックに必要なサイズが見積もれない場合は不便でしょう。 4 アルゴリズム「線形探索」、「二分探索」で特定のデータを検索するための時間計算量をO記法で表し、またその理由も記述せよ。 ※ 探索対象のサイズをNとします。 (線形探索) O(N) 前から順番に調べていくと、平均でN/2回で探索対象を発見できるため。 (二分探索) O(log N) 1回の探索毎に探索範囲を半分に絞り込むことができます。 そのため、探索対象のサイズが2倍になっても、探索回数は平均で1回のみ増加します。 よって、探索回数はlog_2 N(底2のlog)と見積もることができます。 5 データを検索する操作のほうが多い場合と、データを追加する操作が多い場合、 「線形探索」と「二分探索」どちらが有利か理由をつけて述べよ。 データ構造に双方向リストを用いるとします(末尾への追加はO(1))。 (検索が多い)二分探索 新しいデータはリストの順序(昇順・降順)が保たれるような位置に挿入します。 その位置は二分探索で見つけます。 こうしておけば、後でデータを検索する時に二分探索を用いることができますので、 挿入は低速ですが、検索は高速です。 (追加が多い)線形探索 新しいデータはとりあえずリスト最後尾に追加します。 検索が必要な場合はリスト先頭から順に探します。 双方向リストでは、リスト末尾への追加はO(1)ですので、データの追加は高速です。 一方、データはでたらめな順序で並んでしまうので、検索は線形探索で行うしかなく、低速です。

nihuji
質問者

お礼

丁寧な回答ありがとうございます。理解できました。

その他の回答 (2)

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

4 とか 5 は使うデータ構造がわからんので無視して 3 だけ: キューやスタックで要求される操作を思い出して, それを配列やリストで「どのように実装するか」を想像すればわかりやすいかな. キューの方は自明でしょう. スタックはちと微妙. いずれにしても, 1 と関連するネタですな.

nihuji
質問者

お礼

回答ありがとうございます。 考えてみた結果、理解できました。

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

> 自力で頑張れと言われ困っています。 でしたら、自力でできるところまでがんばりましょう。 教科書や参考図書に載っていませんか?

nihuji
質問者

お礼

レジュメや教科書を見て確認したのですが、質問に書いてあること以上はよく分かりませんでした。 よろしくお願いします。

関連するQ&A

  • データ構造とアルゴリズムの問題が分かりません。

    データ構造とアルゴリズムの問題が分かりません。 以下の問題で悩んでいます。 索引は書籍中の単語が書籍の何ページ目に出現するかを表す。もちろん、索引に含まれるある単語が複数のページに出現する場合や、索引に含まれる複数の単語が同一のページに出現する場合もある。 この索引で対象とする単語は、その書籍の中で重要な意味をもつものとして、また、特定の単語はたかだか数ページにのみ出現すると仮定する。 (1)単方向リストを用いてこのようなデータ構造を実現する場合、C言語ではどのように宣言をすれば適切か、struct宣言を用いて示しなさい。 (2)単方向リストを用いてデータ構造の場合、特定の単語が何ページ目に現れるか探すにはどのようなアルゴリズムを適用すれば適切か、探索に必要な時間計算量とともに示しなさい。 (3)二分探索木を用いてこのようなデータ構造を実現する場合、C言語ではどのように宣言をすれば適切か、struct宣言を用いて示しなさい。 (4)二分探索木を用いたデータ構の場合、特定の単語が何ページ目に現れるか探すにはどのようなアルゴリズムを適用すれば適切か、探索に必要な時間計算量とともに示しなさい。 (5)二分探索木を用いたデータ構の場合、アルファベット順の索引を出力するたねには、どのような整列アルゴリズムを適用すれば適切か、整列に必要な時間計算量とともに示しなさい。 テストに類題を出すと先生はおっしゃってたので、どうしてもすぐに回答が必要です。先生にも質問したのですが、テストに類題を出すから教えられない。自力で頑張れと言われ困っています。 どなたか御助力よろしくお願いいたします。

  • 二分探索のアルゴリズム

    分からない問題があります。 ・2分探索における計算量を答えなさい。また、なぜそのようになるのかについてわかりやすく説明しなさい。 ・線形探索の計算量と2分探索の計算量を比べるとどちらの方が計算量が大きいか。理由をつけて説明しなさい。 2分探索の計算量が O(logn) 線形探索の計算量が O(n)となるのはわかりますが そのようになる説明をどのようにしたらいいか。また logn<n となるのは わかるのですが理由をどう説明したらいいのか分かりません。 どなたかお教え下さい。

  • データ構造について

    情報処理技術者試験の過去問で、データ構造について適切な記述を選ぶ問題がありました。回答を見てもいまいちピンときません。 <回答> ※線形リストは、データ部と次のデータの格納先を指すポインタ部から構成されるデータ構造である。 私の持っている本では、 線形リスト:データが順序良く並んできる。配列のこと。 単方向リスト:次のデータのポイントだけを持つ 双方向リスト:前と次のデータへのポインタをもつ 環状リスト:データが環状に連結されている となっています。線形リストにポインタという概念はないってことですよね?なぜ、※の記述が正しいのでしょうか。 わかる方、教えてください。よろしくお願いします。

  • 二分探索アルゴリズムの問題の解法

    二分探索アルゴリズムを用いて、N件のレコードを持つ表の中からキーの値がkに一致するレコードを探し出す探索を考える。この探索について以下の問いに答えよ。 1)このアルゴリズムにおいて最も計算時間が短くなるのは、どのような場合か? 2)このアルゴリズムにおいて最も計算時間が長くなる場合の時間計算量をNのオーダーで表せ。 全くわからないので教えていただいたら、ありがたいです。 一応二分探索なのでO(logN)だけはわかります。 宜しくお願いします。

  • アルゴリズムでわからない問題があります。(C言語)

    問題1:探索アルゴリズムであるハッシュ法について正しいものを選べ。 (1)ハッシュ関数の出力によりデータを格納した配列の先頭から順番に調べる. (2) 入力データを,ハッシュ関数の出力により求めた格納場所に基づいて,あらかじめ木構造に格納しておく. (4) 入力データを格納した配列を繰り返し2つに分割し,それぞれを順番に調べていく. (3) 入力データから格納場所の位置に変換する関数(ハッシュ関数)の出力により,データの探索場所を決定する。 (5) 入力データを,ハッシュ関数の出力により求めた格納場所に基づいて,あらかじめヒープに格納しておく 問題2:探索アルゴリズムであるハッシュ法について正しくないものを選べ。 (1)入力データはハッシュ値で決められる場所に格納される. (2) ハッシュ関数には,異なる入力の値に対し異なる値を出力することが求められる. (3) ハッシュ関数の時間計算量は,入力データのサイズに比例する. (4) データの格納場所が大きい方が効率がよい. (5) 一般に2分探索法より高速に動作する. どなたかアルゴリズムに詳しい方回答お願いします

  • アルゴリズムに関する問題

    こんばんわ、いくつかの問題につまってしまったので解答と簡単な解説をお願いします; 【問1】 4桁の数字( a1a2a3a4 )をハッシュ法を用いて配列に格納したい。 ハッシュ関数をmod( a1 +a2 +a3 +a4 ,5 )とし、求めたハッシュ関数値に対応する位置の配列要素に格納する場合、9576は(ア)~(オ)のどこに入るか。 ここでmod(x,5)の値は、xを5で割った余りとする。 位置  配列 0  (ア) 1  (イ) 2  (ウ) 3  (エ) 4  (オ) 【問2】 相違なるn個のデータが昇順に整列された表がある。この表を1ブロックm個に分割し、各ブロックの最後尾のデータだけ線形検索することによって、目的のデータを探し出す。 次に当該ブロック内を線形検索して目的のデータを探し出す。 このときの平均探索(比較)回数は(ア)~(エ)のうちどれか。 ここでm<nとし、目的のデータは必ず表の中に存在するものとする。 (ア)  (イ)  (ウ)  (エ)  n    n          n    m n  ─    ─    m + ─   ─+─  m    2m         m    2 2m 【問3】 次の手順はシェルソートによる整列を示している。 データ列”7,2,8,3,1,9,4,5,6”を手順(1)~(4)に従って整列すると手順(3)を何回繰り返して完了するか。 ここで、〔〕は小数点以下を切り捨てる。 <手順> (1)〔データ数÷3〕→Hとする。 (2)データ列を互いにH要素分だけ離れた要素の集まりからなる部分列とし、それぞれの部分列を挿入方を用いて整列する。 (3)〔H÷3〕→Hとする (4)Hが0であればデータ列の整列は完了し、0でなければ(2)に戻る。 以上になります。

  • アルゴリズム:2分探索の時間計算量

    アルゴリズムの参考書を読んでいて疑問に思ったんですが、教えてください。 /* 2分探索 */ #include <stdio.h> /*--- 要素数nの配列aからkeyと一致する要素を2分探索 ---*/ int bin_search(const int a[], int n, int key) { int pl = 0;/* 探索範囲先頭の添字【1】 */ int pr = n-1;/* 〃  末尾の添字 【2】*/ int pc; /*   〃  中央の添字 */ do { pc = (pl + pr) / 2;/*【3】*/ if (a[pc] == key) /* 探索成功【4】 */ return (pc);/*【5】*/ else if (a[pc] < key)/*【6】*/ pl = pc + 1;/*【7】*/ else /*【8】*/ pr = pc - 1;/*【9】*/ } while (pl <= pr);/*【10】*/ return (-1);/* 探索失敗【11】 */ } のプログラムがありますが、【1】から【11】までの 実行回数と計算量は次のようになるそうですが、    実行回数   計算量  【1】  1       O(1) 【2】  1       O(1) 【3】  logn     O(logn) 【4】  logn     O(logn) 【5】  1       O(1) 【6】  logn     O(logn) 【7】  logn     O(logn) 【8】  logn     O(logn) 【9】  logn     O(logn) 【10】  logn     O(logn) 【11】  1       O(1) なぜ【3】や【4】がlognになるんでしょうか? 詳しく教えてください。 よろしくお願いします。

  • 高速検索アルゴリズムとデータの追加・削除

    現在高速検索のアルゴリズムを考えておりますが、 そこにデータの追加・削除が絡むと、 どのようにデータをまとめればいいのでしょうか? 例えば ------------ ------------ ------------- |data1|DATA1| |data2|DATA2| |data3|DATA3| ・・・ ------------ ------------ ------------- と要素を2つ持ったデータが複数存在した場合、 dataの昇順リスト ---------------------------- |Index|各データの先頭アドレス| ---------------------------- |・ |・ |・ DATAの昇順リスト ---------------------------- |Index|各データの先頭アドレス| ---------------------------- |・ |・ |・ というそれぞれのリストを持たせれば、 dataで検索したい場合、DATAで検索したい場合、 各リストのIndex値を用いて2分探索すれば高速だと考えました。 しかしデータの追加・削除があればそれぞれのリストを その度にソートし直さなければなりません。 もちろん追加・削除の度にデータ1つ分ずつずらしてやればいいだけですが、 基本的に使わない領域は解放したいですから、データ数の上限値が決まってない以上は 領域も確保されているとは限らないですから安易にデータをずらすことも出来ません。 データのずらしかたもどうでしょう? リストに加えるor削除する箇所からその時の最大値までをコピーして データ1つ分のサイズをずらして貼り付けるといった動作は、 連続した処理や排他的処理を考えると好ましくないのでしょうか? もし根本的に高速検索と追加・削除の相性が良い手法があればご教授願います。

  • データ構造についての質問です。

    データ構造についての質問です。 1.平均16個の子に持つようなB木があり、その深さが3である場合,記録されている   データの個数はどのくらいになるか計算しなさい。 2.B 木に利用するm 分木について,m の値を大きくすればするほど探索効率は良くなる。   正しいか,正しくないか?正しくない場合はその理由を答えなさい。 という2つの問題があります。1番は記録されているデータの個数の計算方法がわかりません。2番はmを大きくすると深さが浅くなるので効率は良くなると思うのですが合っているかわかりません。 どなたかご指導よろしくお願いします。

  • 線形と二分探索により探索を行うプログラムについて教えてください

    20個の配列にデータを入れ(プログラム内で初期化と代入を行って良い)入力した数を探索するプログラムをCmachineで作成したいのですが、線形探索により探索を行うプログラムと二分探索により探索を行うプログラムの作り方を教えていただけないでしょうか?

専門家に質問してみよう