データ構造最終レビュー主観演習(回答版)

8-1隣接リストの適用シナリオ(20点)

質問と回答:隣接リストを使用して無向グラフを格納するのはなぜですか。費用効果が高くなるほどまばらである必要があるのはなぜですか。

答:假设无向图有 n 个点,m 条边,每个点相连 因为邻接表储存无向图的时候,有 n 个顶点就要创建 n 个链表. 每个链表都会存和本顶点相关联的顶点,故每一条边会被存两次。故至少需 m* 2 个节点 而邻接矩阵无论图的稀疏程度,都需要 n*(n+1)/2 的空间存储。

教科書P158;

8-2隣接行列のエッジ(20ポイント)

質問と回答:隣接行列を使用して無向グラフを格納する場合、頂点iと頂点jの間にエッジがあるかどうかを確認するにはどうすればよいですか?

无向图的邻接矩阵 A 是一个对称矩阵,每条边会表示两次,因此矩阵中对应位置 A[i][j] 或 A[j][i]是否为 1,若为 1 则判断有边,为 0 则判断无边。

教科書P155;

8-3二分木一次走査(40ポイント)

次のグラフィックメソッドを使用してバイナリツリーを格納する場合は、対応するタイプ定義を記述し、タイプ定義に基づいてバイナリツリートラバーサルアルゴリズムを記述してください。
ここに画像の説明を挿入

struct BiTNode{
    
      
	char data; 
	int lchild,rchild;  
}Tree[100]; 

void preTraverse(int i){
    
      
	if(i==-1) return ;  
	printf("%d",Tree[i].data);  
	preTraverse(Tree[i].lchild);  
	preTraverse(Tree[i].rchild);  
} 

int main(){
    
        
	preTraverse(1); 
} 

8-4隣接度リスト(5点)

質問と回答:隣接リストを使用して有向グラフを格納するときに、指定された頂点の次数を見つける方法は?

有向グラフの隣接リストが次のようになっているとします。(教科書P156-158)

#define MVNum  100       //最大顶点个数 
typedef struct ArcNode {
    
       
  int   adjvex;   // 该弧所指向的顶点的位置 
  struct ArcNode  *nextarc;   // 指向下一条弧的指针 
  OtherInfo   info;   // 该弧相关的信息,如权值等,若无信息可缺省 
} ArcNode; 
typedef struct VNode {
    
      
  VerTexType  data;   // 顶点信息 
  ArcNode  *firstarc;   // 指向第一条依附该顶点的弧 
} VNode, AdjList[MVNum]; 
typedef struct {
    
       
     AdjList  vertices; 
     int  vexnum, arcnum;  
} ALGraph; 

指定された頂点の次数を見つける

方法1:

有向グラフがALGraphGの場合、指定された頂点Viを見つけて見つけ、位置は1次元配列G.vertices内のiです。

最初に、指定された頂点G.vertices [i]の次数を見つけます。
隣接リストのG.vertices [i]をヘッドノードとし、ポイントされた単一リンクリストをトラバースし、リンクリストの各ノードを順番にトラバースします。 。ノードの数は、頂点の次数です。

次に、指定された頂点G.vertices [i]の次数を見つけます
。G.vertices[1] 〜G.vertices [G.vexnum]内の各単一リンクリストを順番にトラバースし、各単一リンクリストはその頂点をトラバースします。同時にノードを順番に、ノードのadjvexの値がiに等しいかどうかを判断し、等しい場合は、次数のカウンターを1つ増やし、すべてのノードの数をすべてiに等しくします。単一リンクリストは、頂点の次数としてカウントされます。

最後に、頂点の次数は次数+次数です

8-5隣接行列のサイド2(5ポイント)

質問と回答:隣接行列aを使用して、無向ネットワークを格納します。頂点iと頂点jの間にエッジがない場合、a [i] [j]の値は何ですか。また、どのように分析しましたか。

若 i 号顶点与 j 号顶点之间不存在边,则 a[i][j]和 a[j][i]为∞,∞表示计算机允许的、大于所有边上权值的数 Maxn

8-6二分木の順序探索(40ポイント)

次の図を使用して二分木を格納する場合は、次のことを行ってください。
(1)対応する型定義を記述します。
(2)タイプ定義に基づいて、バイナリツリーの順序付き走査アルゴリズムを記述します
(3)関数を呼び出すステートメントを記述します。
ここに画像の説明を挿入

struct BiTNode{
    
      
	char data; 
	int lchild,rchild;  
}Tree[100]; 

void inTraverse(int i){
    
      
	if(i==-1) return ;  
	inTraverse(Tree[i].lchild);  
	printf("%d",Tree[i].data); 
	inTraverse(Tree[i].rchild);  
}  

int main(){
    
        
	inTraverse(1); 
} 

8-7接続および切断1(20ポイント)

1.連結グラフの場合、その連結成分は何ですか?
1) 在无向图中,如果从顶点 vi 到顶点 vj 有路径,则称 vi 和 vj 连通.如果图中任意两个顶点之间都连通,则称该图为连通图,否则,将其中的极大连通子图称为连通分量。任何连通图的连通分量只有一个,即是其自身。

2.無向グラフの任意の頂点からの深さ優先探索ですべての頂点にアクセスできる場合、グラフは何である必要がありますか?
2) 连通图

8-8接続および切断2(20ポイント)

1.連結グラフの場合、その連結成分は何ですか?
1) 在无向图中,如果从顶点 vi 到顶点 vj 有路径,则称 vi 和 vj 连通.如果图中任意两个顶点之间都连通,则称该图为连通图,否则,将其中的极大连通子图称为连通分量。任何连通图的连通分量只有一个,即是其自身。

2.無向グラフの任意の頂点からの幅優先探索ですべての頂点にアクセスできる場合、グラフは何である必要がありますか?
2) 连通图

8-9 DFS読み取りアルゴリズム書き込み演算結果1(30点)

次のアルゴリズム定義を使用します。

void DFS_AM(AMGraph G, int v)
{
    
      //图G为邻接矩阵类型 
  cout << v << " ";  //访问第v个顶点
  visited[v] = true;  
  for(w=0; w<G.vexnum; w++) //依次检查邻接矩阵v所在的行  
     if((G.arcs[v][w]!=0)&& (!visited[w]))  
         DFS_AM(G, w); //w是v的邻接点,如果w未访问,则递归调用DFS_AM 
} 

void DFSTraverse(Graph G)
{
    
      // 对图 G 作深度优先遍历
  for(v=0; v<G.vexnum; ++v) 
     visited[v] = FALSE; //访问标志数组初始化
  for (v=G.vexnum-1; v>=0; --v) 
     if (!visited[v])  DFS(G, v);  //对尚未访问的顶点调用DFS
}

図Gのarcs配列の内容が次のとおりであると想定します。
ここに画像の説明を挿入
実行中のプロセスを記述し、DFSTraverse(G)の結果を出力します。

注:出力結果のみを書き込み、分析プロセスは書き込みません。0ポイント。

v = 7
DFS(G、7)、出力7、visited [7] = TRUE
DFS(G、1)、出力1、visited [1] = TRUE
DFS(G、2)、出力2、visited [2] = TRUE
DFS(G、4)、出力4、visited [4] = TRUE
DFS(G、5)、出力5、visited [5] = TRUE
DFS(G、3)out、出力3、visited [3] = TRUE
DFS(G、5)に戻る
DFS(G、6)出力、出力6、visited [6] = TRUE
DFS(G、5)出力に
戻るDFS(G、4)出力に
戻るDFS(G、2に戻る)出力
DFS(G、1)出力
DFS(G、7)出力
v = 6 v = 5 v = 4 v = 3 v = 2 v = 1 v = 0
DFS(G、0)出力、出力0、visited [0] = TRUE
出力シーケンス:7 1 2 4 5 3 6 0

8-10 DFS読み取りアルゴリズム書き込み演算結果2(30点)

次のアルゴリズム定義を使用します。

void DFS_AM(AMGraph G, int v) 
{
    
      // 图 G 为邻接矩阵类型  
  cout << v << " ";  // 访问第 v 个顶点
 
  visited[v] = true;   
  for(w=G.vexnum-1; w>0; w--) // 依次检查邻接矩阵 v 所在的行   
     if((G.arcs[v][w]!=0)&& (!visited[w]))   
         DFS_AM(G, w); //w 是 v 的邻接点,如果 w 未访问,则递归调用 DFS_AM  
}  
 
void DFSTraverse(Graph G) 
{
    
      // 对图 G 作深度优先遍历
 
  for(v=0; v<G.vexnum; ++v)  
     visited[v] = FALSE; // 访问标志数组初始化
 
  for (v=0; v<G.vexnum; ++v)  
     if (!visited[v])  DFS_AM(G, v);  // 对尚未访问的顶点调用 DFS 
}

図Gのarcs配列の内容が次のとおりであると仮定します。
ここに画像の説明を挿入
実行中のプロセスを記述し、DFSTraverse(G)の結果を出力します。(30ポイント)
注:出力結果のみを書き込み、分析プロセスは書き込みません。0ポイント。

回答:前の質問の回答を参照してください。

8-11単一ソースの最短経路を見つける(20ポイント)

教科書P189図6.35、ダイクストラアルゴリズムを試して、頂点aから他の頂点への最短経路を見つけます。
ここに画像の説明を挿入
(1)初期化後および各反復後にS []、D []、Path []配列の内容を書き込みます。

(2)頂点aと他の頂点の間の最短経路長と対応する経路を書き留めます
ここに画像の説明を挿入
(1)ここに画像の説明を挿入
または
ここに画像の説明を挿入
1-初期化、2-7は6回行います
(2)
ここに画像の説明を挿入
8-12 2つの頂点の間にエッジがあるかどうか(20分)

隣接リストに格納されている有向グラフGに頂点viから頂点vj(i!= j)までのエッジがあるかどうかを判断するアルゴリズムを記述します

有向グラフGの隣接リストが次のようになっていると仮定します。

#define MVNum  100       //最大顶点个数 

typedef struct ArcNode {
    
       
  int   adjvex;   // 该弧所指向的顶点的位置 
  struct ArcNode  *nextarc;   // 指向下一条弧的指针 
  OtherInfo   info;   // 该弧相关的信息,如权值等,若无信息可缺省 
} ArcNode; 

typedef struct VNode {
    
      
  VerTexType  data;   // 顶点信息 
  ArcNode  *firstarc;   // 指向第一条依附该顶点的弧 
} VNode, AdjList[MVNum]; 

typedef struct {
    
       
     AdjList  vertices; 
     int  vexnum, arcnum;  
} ALGraph; 

回答:有向グラフがALGraph Gの場合、1次元配列G.verticesの頂点viの位置はiであり、1次元配列G.verticesの頂点vjの位置はjです。次に、頂点G.vertices [i]をヘッドノードとして単一リンクリストをトラバースし、エッジをトラバースして、現在のノードのadjvexの値がjに等しいかどうかを判断します。等しい場合は、からのエッジがあります。頂点viから頂点vj。それ以外の場合、頂点viから頂点vjへのエッジはありません。

8-13ハッシュテーブルの作成と検索(25ポイント)

キーワードのセットを設定します:(10、16、32、17、31、30、20)、ハッシュ関数は次のとおりです:H(key)= key MOD 11、テーブルの長さは12、線形検出メソッドは競合を処理します。次の質問に答えてみてください。

1.ハッシュテーブルの概略図を描きます。

2.キーワード20を検索する場合、どのキーワードを順番に比較する必要がありますか?

3.キーワード27を検索する場合、どのキーワードを順番に比較する必要がありますか?

4.各キーワードの検索確率が等しいと仮定して、検索が成功したときの平均検索長を見つけます。

5.充填率を見つけます。
ここに画像の説明を挿入
8-14プリム-最小全域木(10ポイント)

次の図では、頂点1から開始して、プリムのアルゴリズムを使用して最小全域木の頂点とエッジのシーケンスを記述します。
ここに画像の説明を挿入
ここに画像の説明を挿入
頂点シーケンス:V = {1,6,2,3,4,0,5}
エッジシーケンス:E = {(1,6)14、(1,2)16、(2,3)12、(3、 4)22、(6,0)23、(0,5)、10)

8-15隣接リストに従ってグラフの幅優先走査シーケンスを記述します(10ポイント)

(1)下図の隣接リストを書き出します(エッジノードのシーケンス番号は小さいものから大きいものへ)。

(2)頂点間のスペースで区切って、頂点3から始まる幅優先探索シーケンスと深さ優先探索シーケンスを記述します。少数のノードの優先順位で訪問することが合意されています。(答えは写真に挿入できます)
ここに画像の説明を挿入
ここに画像の説明を挿入
8-16二分探索木の構築(5点)

12,7,17​​,11,16,2,13,9,21,4のキーシーケンスを空の二分木に順番に挿入します。結果の二分木を描画してください。
ここに画像の説明を挿入

ここに画像の説明を挿入

8-17二分探索(5ポイント)

次の11個の要素(8、16、19、23、39、52、63、77、81、88、90)の順序付きリストを前提として、そのバイナリ検索の決定木を描画し、検索要素88と17を指定します。二分探索プロセス。
ここに画像の説明を挿入

デシジョンツリーの概念については、教科書P194を参照してください。

8-18ヒープソートの初期ヒープ(6ポイント)

レコードグループのキーコードが(46,79,56,38,40,84)の場合、ヒープソート方式で作成した初期ヒープを記述してください。詳細なプロセス(3点)と結果(3点)を書いてください。

教科書P252を参照してください。例8.6:最後の非終端ノードからスクリーニングを開始します。

ここに画像の説明を挿入
結果:84、79、56、38、40、46;

8-19ハフマンツリーの構築(9ポイント)

通信に使用するメッセージが8文字のみであるとすると、メッセージに現れる文字の頻度は、それぞれ0.09、0.16、0.02、0.06、0.32、0.03、0.21、0.11です。

(1)これらの8文字のハフマンコードを設計してみてください。ハフマンツリー構築の詳細なプロセスとコードを書き留めてください。(4ポイント)

(2)バイナリで表される別の等長コーディングスキームを設計します;(2ポイント)

(3)上記の例では、2つのスキームのコーディング長を分析し、2つのスキームの長所と短所を分析します(3ポイント)

回答:
(1)①初期化:最初に2 8 = 16ユニットに動的に適用し、次にユニット1から開始して2 8-1 = 15回ループし、1からすべてのユニットに親、左子、右子を順番に追加します。 15の添え字は0に初期化され、最後のサイクルは8回で、最初の8ユニットのリーフノードの重みが入力されます
。②ツリーの作成:サイクル8-1 = 7回、n-1 =まで選択して削除します。 7回マージしてハフマンツリーを作成します。選択は、親が0で現在のフォレストから最小の重みを持つ2つのツリールートノードs1とs2を選択することです。削除は、ノードs1とs2の親をゼロ以外に変更することを意味します。マージは、の重みを変更することです。 s1とs2新しいノードの重みとしての合計は、配列のn + 1 = 9の後にユニットに順次格納され、この新しいノードの左の子の添え字はs1として記録され、右の添え字は子はs2です。
ここに画像の説明を挿入
ここに画像の説明を挿入
コーディング:
A:000
B:110
C:11100
D:1111
E:10
F:11101
G:01
H:001

(2)(3)
ここに画像の説明を挿入

おすすめ

転載: blog.csdn.net/Jessieeeeeee/article/details/107390119