課題を教えてください

フォーラム(掲示板)ルール
フォーラム(掲示板)ルールはこちら  ※コードを貼り付ける場合は [code][/code] で囲って下さい。詳しくはこちら
ほがら

課題を教えてください

#1

投稿記事 by ほがら » 2年前

コード:

#include <stdio.h>
#include <stdlib.h>

// 構造体宣言 
// スタック用
typedef struct stack{
	int val;
	struct stack* next;
} STACK;

// キュー用
typedef struct node{
	int val;
	struct node* next;
} NODE;

typedef struct queue{
	【①】// 「先頭」を表すポインタの宣言
	【②】// 「末尾」を表すポインタの宣言
} QUEUE;

// プロトタイプ宣言 
STACK* push(STACK* stack, int val);		// スタック用
int pop(STACK** stack);
QUEUE* enqueue(QUEUE* queue, int val);	// キュー用
int dequeue(QUEUE** queue);

// メイン関数
int main(int argc, char** argv){
	STACK *stack = NULL; // スタック
	QUEUE *queue = NULL; // キュー
	int i, val;

	// スタック・キューへの初期値格納
	int init[] = {1, 2, 3};
	for(i = 0 ; i < 3 ; i++){
		stack = push(stack, init[i]);
		queue = enqueue(queue, init[i]);
	}
	printf("\n");

	// push&popテスト
	printf("スタック1つめ: %d\n", pop(&stack));
	printf("スタック2つめ: %d\n", pop(&stack));

	// 標準入力による値の追加
	scanf("%d", &val);
	stack = push(stack, val);
	scanf("%d", &val);
	stack = push(stack, val);

	printf("スタック残り: \n");
	for(i = 0 ; i < 3 ; i++){
		printf("\t%d\n", pop(&stack));
	}
	printf("\n");

	// enqueue&dequeueテスト
	printf("キュー1つめ: %d\n", dequeue(&queue));
	printf("キュー2つめ: %d\n", dequeue(&queue));

	// 標準入力による値の追加
	scanf("%d", &val);
	queue = enqueue(queue, val);
	scanf("%d", &val);
	queue = enqueue(queue, val);

	printf("キュー残り: \n");
	for(i = 0 ; i < 3 ; i++){
		printf("\t%d\n", dequeue(&queue));
	}
	printf("\n");

	return 0;
}

// プッシュ関数
STACK* push(STACK* stack, int val){
	STACK* tmpstack; 

	tmpstack = 【③】; // スタック初期化
	tmpstack->val = val;
	【④】 // stackがtmpstackの次に来るように代入

	return tmpstack;
}

// ポップ関数
int pop(STACK** stack){
	int tmpval;

	if(*stack != NULL){
		tmpval = (*stack)->val;
		【⑤】 // stackをひとつ進めてpop処理を実行
	}

	return tmpval;
}

// キュー挿入関数
QUEUE* enqueue(QUEUE* queue, int val){
	// キューが空のとき
	if(queue == NULL){
		queue = 【⑥】; // キュー初期化
		queue->head = (NODE*)malloc(sizeof(NODE));
		queue->head->val = val;
		【⑦】; // キューの末尾初期値として先頭アドレスを代入
	}
	// キューが空でないとき
	else{
		【⑧】 // 末尾の次に新規ノードの領域割り当て
		queue->tail->next->val = val;
		queue->tail = queue->tail->next;
	}

	return queue;
}

// キュー取り出し関数
int dequeue(QUEUE** queue){
	int tmpval;

	【⑨】 // tmpvalに先頭ノードの値を渡す
	(*queue)->head = (*queue)->head->next;

	return tmpval;
}
穴埋めの課題です。スタック,キューによる数値の格納・取出しを行うプログラムになります。
①int *head;
②int *tail;
③(NODE*)malloc(sizeof(NODE));
④tmpstack->next = stack;
⑤pop(stack++);
⑥(NODE*)malloc(sizeof(NODE));
⑦queue->tail = queue->head
⑧queue->tail->next;
⑨tmpval = queue->head;

を入れてますが⑧と⑨は違うんだろうなと思っています。良ければ教えてください。

アバター
みけCAT
記事: 6734
登録日時: 13年前
住所: 千葉県
連絡を取る:

Re: 課題を教えてください

#2

投稿記事 by みけCAT » 2年前


intではなく、ノードを指すポインタを用意するべきです。

コード:

NODE* head;

intではなく、ノードを指すポインタを用意するべきです。

コード:

NODE* tail;

【③】はSTACK*型の変数に代入されているのに、NODE*を代入するというのは不自然ですね。
セミコロンは【③】の後にあるので不要ですが、あっても害は無いです。 (空文が増えるだけ)

コード:

malloc(sizeof(*tmpstack))

正しいと思います。


これではpop関数内でpop関数を同じ引数で呼び出す(後置インクリメントはインクリメント前の値に評価される)
ので、無限再帰になってしまいます。
「ひとつ進めて」とは、次のノードを指すようにする、ということでしょう。

コード:

*stack = (*stack)->next;

【⑥】はQUEUE*型の変数に代入されているのに、NODE*を代入するというのは不自然ですね。
セミコロンは【⑥】の後にあるので不要ですが、あっても害は無いです。 (空文が増えるだけ)

コード:

malloc(sizeof(*queue))

正しいと思います。


領域を割り当てるには、領域を確保して代入します。

コード:

queue->tail->next = malloc(sizeof(*queue->tail->next));

先頭ノードそのものではなく、先頭ノードの値を渡さないといけません。
また、queueが指しているのはQUEUE*であり、そこにはheadメンバはありません。

コード:

tmpval = (*queue)->head->val;
複雑な問題?マシンの性能を上げてOpenMPで殴ればいい!(死亡フラグ)

返信

“C言語何でも質問掲示板” へ戻る