33,000원
다른 수강생들이 자주 물어보는 질문이 궁금하신가요?
- 미해결홍정모의 따라하며 배우는 C언어 (부록)
이진 탐색: 탐색 실패하는 경우 어째서 first > last인 경우가 나오나요?
17.15강 이진탐색 강의의 13:10부분입니다.이진탐색에서 만약 탐색을 실패하는 경우 어째서 first >last라는 상황이 발생하는지 잘 모르겠습니다.반복문을 반복해야할 상황이(탐색해야할 상황이) first <= last인 상황이라는 것을 알겠지만, first > last가 되는 상황은 어떻게 유도되는지 모르겠습니다.#include <stdio.h> int BSearch(int ar[], int len, int target) { int first = 0; int last = len - 1; int mid; while (first <= last) { mid = (first + last) / 2; if (target == ar[mid]) return mid; else { if (target < ar[mid]) last = mid - 1; else first = mid + 1; } } return -1; } int main(void) { int arr[] = { 1,3,5,6,7,9,11,13,15,19 }; int index; index = BSearch(arr, sizeof(arr) / sizeof(int), 3); if (index == -1) printf("해당값 없음\n"); else printf("타겟의 위치 : %d\n", index); return 0; }
- 미해결홍정모의 따라하며 배우는 C언어 (부록)
17.12) access violation
#pragma once #include <stdbool.h> #define TSIZE 45 #define MAX_SIZE 4 // array size typedef struct element { char name[TSIZE]; } Item; typedef struct queue { int front; int rear; int n_items; Item items[MAX_SIZE]; } Queue; void Init_queue(Queue* pq); bool QueueIsFull(const Queue* pq); bool QueueIsEmpty(const Queue* pq); int QueueItemCount(const Queue* pq); bool Enqueue(Item item, Queue* pq); bool Dequeue(Item* pitem, Queue* pq); void EmptyQueue(Queue* pq); void TraverseQueue(Queue* pq); void print_item(Item item); #include "ArrayQueue.h" #include <stdio.h> #include <assert.h> void Init_queue(Queue* pq) { pq->front = 0; pq->rear = 0; pq->n_items = 0; } bool QueueIsFull(const Queue* pq) { return (pq->rear + 1) % MAX_SIZE == pq->front; } bool QueueIsEmpty(const Queue* pq) { return pq->front == pq->rear; } int QueueItemCount(const Queue* pq) { return pq->n_items; } bool Enqueue(Item item, Queue* pq) { if (QueueIsFull(pq)) { printf("Queue is Full.\n"); return false; } pq->rear = (pq->rear + 1) % MAX_SIZE; pq->items[pq->rear] = item; pq->n_items++; return true; } bool Dequeue(Item* pitem, Queue* pq) { if (QueueIsEmpty(pq)) { printf("Queue is Empty.\n"); return false; } pq->front = (pq->front + 1) % MAX_SIZE; *pitem = pq->items[pq->front]; pq->n_items--; return true; } void EmptyQueue(Queue* pq) { Init_queue(pq); } void TraverseQueue(Queue* pq) { for (int i = pq->front; i != pq->rear; i = (i + 1) % MAX_SIZE) print_item(pq->items[(i + 1) % MAX_SIZE]); } void print_item(Item item) { printf('%s ', item.name); } #include <stdio.h> #include <string.h> #include "ArrayQueue.h" Item get_item(const char* name); void print_queue(Queue* pq); int main() { Queue queue; Item temp; Init_queue(&queue); Enqueue(get_item("Jack"), &queue); print_queue(&queue); Enqueue(get_item("Henry"), &queue); print_queue(&queue); Enqueue(get_item("Stan"), &queue); print_queue(&queue); Enqueue(get_item("Butters"), &queue); // capacity 4/3 fail print_queue(&queue); if (Dequeue(&temp, &queue)) printf("Item from queue : %s\n", temp.name); print_queue(&queue); if (Dequeue(&temp, &queue)) printf("Item from queue : %s\n", temp.name); print_queue(&queue); if (Dequeue(&temp, &queue)) printf("Item from queue : %s\n", temp.name); print_queue(&queue); if (Dequeue(&temp, &queue)) printf("Item from queue : %s\n", temp.name); print_queue(&queue); printf("====== Circulation Test ======"); Init_queue(&queue); for (int i = 0; i < 10; ++i) { Enqueue(get_item("Hello"), &queue); print_queue(&queue); if (Dequeue(&temp, &queue)) printf("Item from queue : %s\n", temp.name); print_queue(&queue); } return 0; } Item get_item(char* name) { Item new_item; strcpy(new_item.name, name); return new_item; } void print_queue(Queue* pq) { printf("Front : %d, Rear : %d, Size %d\n", pq->front, pq->rear, pq->n_items); printf("Queue : "); if (QueueIsEmpty(pq)) printf("Empty"); else TraverseQueue(pq); printf("\n\n"); } 순서대로 헤더, 헤더함수파일, 메인파일 입니다 디버깅시, TraverseQueue함수 내의 print_item 함수가 실행되는 순간 access violation이 뜹니다access violation 전까지는 값들 제대로 다 연산이 되다가갑자기 print함수에서 저러니까 도저히 감이 안잡힙니다방법이 없어 도움을 구합니다
- 미해결홍정모의 따라하며 배우는 C언어 (부록)
finditembyindex 질문드립니다!
위 함수에서, Item** item 이중포인터로 받아오는 이유를 여쭤봐도 될까요?? 제가 생각한 것은 Item* item을 변수로 받고, 219번 line을 item = &pnode -> item; 으로 해도 문제가 없을 것이라고 생각하는데, 어떤 개념을 놓치고 있는지 알고 싶습니다 감사합니다
- 해결됨홍정모의 따라하며 배우는 C언어 (부록)
19:20 부분에서 질문있습니다.
교수님께서 Seekitem()를 이용해서 pair를 return하는 방법에는 while문을 사용하는 방법 말고도 재귀호출을 사용하는 방법도 있다고 하셨습니다. 저는 재귀호출로 짜봤는데 아무래도 너무 지저분한 거 같습니다. 교수님이나 다른 분이 재귀호출을 사용하셨다면 어떤 식으로 코드를 짰을 지가 궁금합니다.제가 짠 코드는 아래와 같습니다. static Node* SeekParentNode(const Item* pi, Node* pnode) { if (pnode->left != NULL) if (compare(pnode->left->item, *pi) == 0) return pnode; if (pnode->right != NULL) if (compare(pnode->right->item, *pi) == 0) return pnode; if (compare(pnode->item, *pi) > 0) { if (pnode->left == NULL && pnode->right == NULL) return NULL; SeekParentNode(pi, pnode->left); } else if (compare(pnode->item, *pi) < 0) { if (pnode->left == NULL && pnode->right == NULL) return NULL; SeekParentNode(pi, pnode->right); } } static Node* SeekChildNode(const Item* pi, Node* pnode) { if (compare(pnode->item, *pi) == 0) return pnode; if (compare(pnode->item, *pi) > 0) { if (pnode->left == NULL) return NULL; SeekChildNode(pi, pnode->left); } else { if (pnode->right == NULL) return NULL; SeekChildNode(pi, pnode->right); } } static Pair SeekItem(const Item* pi, const Tree* ptree) { Pair found_pair; found_pair.parent = SeekParentNode(pi, ptree->root); found_pair.child = SeekChildNode(pi, ptree->root); return found_pair; }
- 미해결홍정모의 따라하며 배우는 C언어 (부록)
pnode = pnode->next; 와 pnode->next = pnode;는 같은 것으로 생각해도 될까요?
예를 들어서 pnode->title과 입력받은 title의 값이 맞는지 비교하는 코드에서 while (pnode != NULL) { if (strcmp(pnode->title, title) == 0) break; //pnode->next = pnode;// pnode의 next node에다가 pnode를 대입 pnode = pnode->next;//pnode에다가 pnode의 next 노드의 주소를 대입 count++; } 이렇게 되어 있을때 pnode = pnode->next; 와 pnode->next = pnode;는 같은 기능을 하는 것으로 생각해도 될까요? 그런 것 같긴 한데 알쏭달송해서 질문해봅니다
- 해결됨홍정모의 따라하며 배우는 C언어 (부록)
질문. warning뜨는 이유
안녕하세요. c6385와 c6386warning이 뜨는 이유가 궁금합니다. 동적할당하고 배열 index도 잘 참조한거 같은데 warning이 안 지워지더라고요..ㅠ 오류 처리 때문인지 교수님 오류처리 코드도 다 따라 쳐 보았지만 소용이 없네요. #include <stdio.h> #include <stdlib.h> #include <String.h> #define LENGTH 100 struct movieinfo { char subj[LENGTH]; double score; }; void manual(void); void print_all_items(struct movieinfo* msptr, int* num); void print_an_item(struct movieinfo* msptr, int* num); void edit_an_item(struct movieinfo* msptr, int* num); void add_an_item(struct movieinfo** mmsptr, int* num); void insert_an_item(struct movieinfo** mmsptr, int* num); void delete_an_item(struct movieinfo** mmsptr, int* num); void delete_all_items(struct movieinfo* msptr, int* num); void save_file(struct movieinfo* msptr, int* num); void search_by_name(struct movieinfo* msptr, int* num); int main() { int input; printf("Please input filename to read press Enter.\n>> "); char fname[LENGTH] = { 0, }; scanf("%s", fname); char a = getchar(); FILE* fmovie = fopen(fname, "r"); if (!fmovie) { perror("ERROR: cannot open file."); exit(1); } puts("6 items have been read from the file.\n"); int num; if (fscanf(fmovie, "%d%*c", &num) != 1) { printf("ERROR: Wrong file format."); exit(1); } struct movieinfo* msptr = (struct movieinfo*)malloc(sizeof(struct movieinfo) * num); if (msptr == NULL) { printf("malloc failed. \n"); exit(1); } for (int i = 0; i < num; i++) { if(fscanf(fmovie, "%[^\n]%*c", msptr[i].subj) != 1 || fscanf(fmovie, "%lf%*c", &msptr[i].score) != 1) { printf("ERROR: Wrong file format.\n"); exit(1); } } while (1) { manual(); scanf("%d%*c", &input); switch (input) { case 1: print_all_items(msptr, &num); break; case 2: print_an_item(msptr, &num); break; case 3: edit_an_item(msptr, &num); break; case 4: add_an_item(&msptr, &num); break; case 5: insert_an_item(&msptr, &num); break; case 6: delete_an_item(&msptr, &num); break; case 7: delete_all_items(msptr, &num); break; case 8: save_file(msptr, &num); break; case 9: search_by_name(msptr, &num); break; case 10: puts("Good bye"); free(msptr); fclose(fmovie); return 0; default: printf("Wrong input.\n"); break; } } free(msptr); fclose(fmovie); return 0; } void manual(void) { printf("Please select an option and press enter.\n"); printf("1. print all items\t2. print an item\n"); printf("3. Edit an item \t4. Add an item\n"); printf("5. Insert an item\t6. Delete an item\n"); printf("7. Delete all items\t8. Save file\n"); printf("9. Search by name\t10. Quit\n>> "); } void print_all_items(struct movieinfo* msptr,int *num) { for (int i = 0; i < *num; i++) { printf("%i : \"%s\". %.1f\n",i, msptr[i].subj, msptr[i].score); } } void print_an_item(struct movieinfo* msptr, int *num) { printf("Input the index of item to print.\n>> "); int input; scanf("%d%*c", &input); if (input<0 || input>*num) printf("invalid item\n"); else printf("%i : \"%s\". %.1f\n", input, msptr[input].subj, msptr[input].score); } void edit_an_item(struct movieinfo* msptr, int* num) { printf("Input the index of item to print.\n>> "); int input; scanf("%d%*c", &input); if (input<0 || input>*num) printf("invalid item\n"); else printf("%i : \"%s\". %.1f\n", input, msptr[input].subj, msptr[input].score); printf("Input new title and press enter.\n>> "); scanf("%[^\n]%*c", msptr[input].subj); printf("Input new rating and press enter.\n>> "); scanf("%lf%*c", &msptr[input].score); printf("%i : \"%s\". %.1f\n", input, msptr[input].subj, msptr[input].score); } void add_an_item(struct movieinfo** mmsptr, int* num) { int flag; *num = *num + 1; struct movieinfo* msptr = (struct movieinfo*)malloc(sizeof(struct movieinfo) * *num); if (msptr == NULL) { printf("malloc failed. \n"); exit(1); } for (int i = 0; i < *num - 1; i++) { strcpy(msptr[i].subj, (*mmsptr)[i].subj); msptr[i].score = (*mmsptr)[i].score; } printf("Input title and press enter.\n>> "); flag = scanf("%[^\n]%*c", msptr[*num - 1].subj); printf("Input rating and press enter.\n>> "); flag = scanf("%lf%*c", &msptr[*num - 1].score); printf("%i : \"%s\". %.1f\n", *num - 1, msptr[*num - 1].subj, msptr[*num - 1].score); free(*mmsptr); *mmsptr = msptr; } void insert_an_item(struct movieinfo** mmsptr, int* num) { printf("Input the index of item to insert.\n>> "); int input; scanf("%d%*c", &input); *num = *num + 1; struct movieinfo* msptr = (struct movieinfo*)malloc(sizeof(struct movieinfo) * *num); if (msptr == NULL) { printf("malloc failed. \n"); exit(1); } for (int i = 0; i < *num - 1; i++) { strcpy(msptr[i].subj, (*mmsptr)[i].subj); msptr[i].score = (*mmsptr)[i].score; } int imp = *num; for (; imp - 1 > input; imp--) { strcpy(msptr[imp - 1].subj, msptr[imp - 2].subj); msptr[imp - 1] = msptr[imp - 2]; } printf("Input title and press enter.\n>> "); scanf("%[^\n]%*c", msptr[input].subj); printf("Input rating and press enter.\n>> "); scanf("%lf%*c", &msptr[input].score); printf("%i : \"%s\". %.1f\n", input, msptr[input].subj, msptr[input].score); free(*mmsptr); *mmsptr = msptr; } void delete_an_item(struct movieinfo** mmsptr, int* num) { printf("Input the index of item to delete.\n>> "); int input; scanf("%d%*c", &input); *num = *num - 1; struct movieinfo* msptr = (struct movieinfo*)malloc(sizeof(struct movieinfo) * *num); if (msptr == NULL) { printf("malloc failed. \n"); exit(1); } int imp = input; for (; input < *num; input++) { strcpy((*mmsptr)[input].subj, (*mmsptr)[input + 1].subj); (*mmsptr)[input].score = (*mmsptr)[input + 1].score; } for (int i = 0; i < *num; i++) { strcpy(msptr[i].subj, (*mmsptr)[i].subj); msptr[i].score = (*mmsptr)[i].score; } free(*mmsptr); *mmsptr = msptr; } void delete_all_items(struct movieinfo* msptr, int* num) { *num = 0; msptr = NULL; } void save_file(struct movieinfo* msptr, int* num) { printf("Please input filename to write and press Enter.\n>> "); char fname[LENGTH] = { 0, }; scanf("%s", fname); FILE* fmovie = fopen(fname, "w"); fprintf(fmovie, "%d\n", *num); for (int i = 0; i < *num; i++) { fprintf(fmovie, "%s\n%.1lf\n", msptr[i].subj, msptr[i].score); } printf("%d items have been saved to the file.\n",*num); fclose(fmovie); } void search_by_name(struct movieinfo* msptr, int* num) { printf("Input title to search and press enter.\n>> "); char strcm[LENGTH] = { 0, }; scanf("%[^\n]%*c", strcm); int i; for (i = 0; i < *num; i++) { if (strcmp(strcm, msptr[i].subj) == 0) break; } if (i == *num) printf("No movie found : %s\n", strcm); else printf("%i : \"%s\". %.1f\n", i, msptr[i].subj, msptr[i].score); }
- 미해결홍정모의 따라하며 배우는 C언어 (부록)
링크드 리스트 질문 드립니다.
while (search != NULL) search = search->next; search = new_node; new_node->next = NULL; 이 코드에서 search가 링크드 리스트의 마지막 노드의 next 주소를 가지고 있는거 아닌가요? 그래서 new_node의 주소를 대입하는 것과while (search->next != NULL) search = search->next; search->next = new_node; new_node->next = NULL;이코드에서 search가 마지막 노드의 주소를 가지고 있고, 그래서 next에 new_node의 주소를 넘겨주는 것과 무슨 차이가 있는지 모르겠습니다. 아래코드는 정상 작동하고 위에 코드가 작동하지 않습니다.
- 해결됨홍정모의 따라하며 배우는 C언어 (부록)
함수포인터 질문드립니다
안녕하세요 main.c 함수에서 void write_file(const List * const plist) 내에 있는 unsigned int count = WriteAllItems(plist, file, &write_an_item); 에서는 &write_an_item을 주소값으로 넘기고 void print_all(const List* plist) 내에 있는 PrintAllItems(plist, print_an_item); 함수에서는 print_an_item을 주소값이 아닌 그냥 함수자체로 넘기는데 왜 두개가 다른 방식으로 넘기는지 궁금합니다
- 미해결홍정모의 따라하며 배우는 C언어 (부록)
강의 내용 질문 드립니다!
강의 16분경, if (prev==NULL) 부분에 대하여 질문드립니다!위에서 prev = NULL 로 초기화를 해주었고,1.search 하는 루프에 아예 진입하지 못하거나,2.search 루프에 들어가자마자 찾아서 break; 에 걸리거나두 경우가 아니면 prev가 null 일수 없는 구조로 보이는데, 설명하시기를, prev 가 null이다 -> prev가 head이다 라고 하신 부분이 이해가 잘 가지 않습니다!prev가 null이다 -> search가 head일 때가 아닌지 여쭙습니다ㅜㅜ 제가 이해가 부족한 것이라면 도움 부탁드리겠습니다. 감사합니다!
- 미해결홍정모의 따라하며 배우는 C언어 (부록)
노드 주소 순서 관련 질문
안녕하세요! 항상 좋은강의 감사드립니다. 연결 리스트에서 노드의 주소가 배열처럼 일련/오름차순으로 배치가 되는것은 아닌거죠? 각 노드는 주소의 크기에 관계없이 랜덤으로 분포해있고 그 노드 주소를 순서대로 연결시키는 개념이 맞는지 궁금해서 질문드렸습니다.
- 미해결홍정모의 따라하며 배우는 C언어 (부록)
질문드립니다!
안녕하세요 교수님, 전 따배씨에 이어 부록 강의도 열심히 수강하고 있는 학생입니다. 이번강의를 보다가 이해가 가지않는 부분이 있어 질문드립니다. 강의 32:19초에 나오는 RemoveNextItem 함수에서 258번째줄에 있는 temp = prev -> next -> next ; 가 전달하는 의미를 잘 모르겠습니다. 어떻게이해하면 될까요??
- 미해결홍정모의 따라하며 배우는 C언어 (부록)
DeleteAllNodes 에서 질문있습니다.
안녕하세요 . 교수님의 DeleteAllNodes 코드는 아래와같습니다. void DeleteAllNodes(Node*root){ if (root == NULL) { return; } Node* pright = root->right; DeleteAllNodes(root->left); free(root); DeleteAllNodes(pright); } 하지만 이 코드는 Tree의 root 를 NULL로 바꿔주지못해 실제 활용시 에러를 발생시키는데요 따라서 Node**ptr 을 Parameter로 사용하거나 Tree를 활용해야하는데 재귀호출을 사용하다보니 Node**ptr을 Parameter로 받기는 조금 번거롭고 따라서 Tree를 활용하기위해 아래와같이 DeleteAllItems 라는 함수를 따로만들어 void DeleteAllNodes(Node*root) { /* if (root == NULL) { return; } Node* pright = root->right; DeleteAllNodes(root->left); free(root); DeleteAllNodes(pright); */ if (root == NULL) { return; } Node* pright = root->right; if (root->left != NULL) { DeleteAllNodes(root->left); } free(root); if (root->left != NULL) { DeleteAllNodes(pright); } } void DeleteAllItems(Tree* tree) { if (tree->root == NULL) { return; } DeleteAllNodes(tree->root); tree->root = NULL; tree->m_items = 0; } 이렇게 구현하는것이 더 좋지않나 싶은데 선생님은 어떻게 생각하시나요?
- 미해결홍정모의 따라하며 배우는 C언어 (부록)
16:30 질문입니다.
안녕하세요 큐의 정의조건에는 "아이템이 한개또는 0개일때는 front와 rear포인터의 값이 같다" (전자는 해당 노드의 주소 후자는 Null) 가 있는데요 강의 16:30 bool DeQue 함수를 보면 교수님의 코드는 큐가 빌경우 front 와 rear의 값이 Null로 같아지는 경우는 구현했으나 원소가 하나일때 둘이 같아지게 하는 코드가 없는것같습니다. 아래는 조잡하지만 제가 구현한 코드인데요 bool DeQue(Item*item , Queue*pq) { if(pq->first==Null) { printf("empty₩n"); return false;} Node*temp=pq->front->next; *item=pq->front->item; free(pq->front); pq->front=head; pq->size-=1; if(pq->front==Null ll pq->front->next==Null) { pq->rear=pq->front;} return true; } 마지막 if처럼 둘이서로 같게해주는 코드가 필요하다 보는데 어떻게 생각하시나요?
- 해결됨홍정모의 따라하며 배우는 C언어 (부록)
scanf 질문이요!!
9:48분경 edit_an_item함수 내부에서 scanf를 사용한후 반환값을 f로 받던대 왜 받는거죠?? f값을 따로 사용하지도 않는것 같은대?? 받는이유가 있나요??
- 미해결홍정모의 따라하며 배우는 C언어 (부록)
12:30 의 ArrayQueue.h
12:30 의 ArrayQueue.h의 struct element {charname[TIZE];} element; 로 구조체 element 타입에 대한 element라는 객체를 선언하고있는데요 , 굳이 그럴필요가 있나요? 단순히 구조체element만을 선언해도 되지않나 싶은데 어떻게 생각하시나요?
- 미해결홍정모의 따라하며 배우는 C언어 (부록)
10:10 Add front에서 질문드립니다.
안녕하세요. 10:10 Add front 부분에서 p_movie temp=head; 코드를 생략하고 new_node->next = head; head = new_node; 이렇게만 해줘도 결과가 같은데. 상관 없나요?
- 미해결홍정모의 따라하며 배우는 C언어 (부록)
스택 자료구조
스택 자료구조에 대해 조금 궁금증이 생겨서 질문 남깁니다. 연습 문제를 풀 때 pop element Pop(Stack* stack) { if (IsEmpty(stack) == true) { element tempt = { -1 }; printf("Stack is Empty. Cannot remove\n"); return tempt; } else { return stack->items[stack->top--]; } } 이것을 구현 하는데 오랜 시간이 걸렸는데, 이유가 이미 쌓인 메모리를 아에 지우려고 시도해서 입니다. 그런데 코드를 보면 stack->top 을 인덱스 처럼 이용해서 stack->top의 값만 바꾸어 주며 사실 저장된 값은 그대로 있어서 사용하지도 않는 값을 가지고 있는게 아닌가 하는 의문이 들었습니다. 앞에서 배운 linked-list의 경우는 free를 이용하여 메모리를 지워주는데 스택의 메모리는 계속 쌓여있는 것이 아닌가요?
- 해결됨홍정모의 따라하며 배우는 C언어 (부록)
변수 count의 활용에 대해 질문이 있습니다.
안녕하세요 선생님^^ 좋은 강의 제공해주심에 감사드립니다.강의 중 코드 내용에 대해 궁금한 점이 있어 질문드립니다. Find and delete an item 부분(91행 이후, 강의시간 기준 15:00 )에서의 질문입니다. Q. 0으로 초기화되어 선언된 count(int count = 0;)는 용도가 어떻게 되나요?- 이해가 깊지 못하여, 본 예제에 제공된 코드가 실행되는 범위 내에선 그 사용도를 알지 못하겠습니다. - 혹시 반복문이 실행됨에 따른 count의 변화를 통해 몇 번만에 갔는지를 체크하는 등의 목적을 가진 용도로 작성하셨던 건가요? 항상 좋은 강의 감사드립니다.건강하십시오. :)
- 미해결홍정모의 따라하며 배우는 C언어 (부록)
1번 실행하면 에러가 뜨는데 이유를 모르겠습니다..
#define _CRT_SECURE_NO_WARNINGS #include <stdio.h> #include <conio.h> #include <stdlib.h> #include <assert.h> #include <string.h> #define TSIZE 45 #define LMAX 10 struct movie { char title[TSIZE]; float rating; }; void read_file(struct movie movie_list[], int* ptr_n_items) //값 바꿀수 잇어야 하므로 포인터로 저장 { char filename[TSIZE] = { 0, }; //버퍼역할을 하는 문자의 배열 printf("읽기위한 파일 이름 입력후 엔터 눌르셈"); printf(">>"); if (scanf("%[^\n]%*c", filename) != 1) { printf("Wrong input. Terminating\n"); exit(1); } FILE* file = fopen(filename, "r"); if (file == NULL) { printf("에러 : 파일 열 수 없음"); exit(1); } int num; //파일 몇개인지 읽는 거 if (fscanf(file, "%d%*c", &num) != 1) { printf("ERROR: 잘못된 파일 포맷"); exit(1); } for (int n = 0; n < num; ++n) { if (fscanf(file, "%[^\n]%*c", movie_list[*ptr_n_items].title) != 1 || fscanf(file, "%f%*c", &movie_list[*ptr_n_items].rating) != 1) { printf("ERROR 잘못된 파일 형식"); exit(1); } *ptr_n_items += 1; } assert(*ptr_n_items == num); fclose(file); printf("%d items have been read from the file\n", *ptr_n_items); } void write_file(struct movie movie_list[], int n_items) { char filename[TSIZE] = { 0, }; printf("파일 이름 입력하고 엔터 쳐주세요"); printf(">>"); if (scanf("%[^\n]%*c", filename) != 1) { printf("Wrong input . Terminating\n"); exit(1); } FILE* file = fopen(filename, "w"); if (file == NULL) { printf("ERROR : 파일 못염\n"); exit(1); } fprintf(file, "%d\n", n_items); for (int n = 0; n < n_items; ++n) { fprintf(file, "%s\n", movie_list[n].title); fprintf(file, "%f\n", movie_list[n].rating); } fclose(file); printf("%d items have been saved to the file\n", n_items); } int input_int() //사용자로부터 정수 입력 받는 경우 많기떄문에(자주 사용해서 하나 만듬) { int input; while (1) { printf(">>"); if (scanf("%d%*c", &input) == 1) return input; else { printf("숫자 입력후 엔터 눌러주세요\n"); while (getchar() != '\n') continue; } } } int input_menu() { while (1) { printf("\n 옵션 선택후 엔터 눌러주세요\n"); printf("1.print all items 2. print an item\n"); printf("3.Edit an item 4. add an item\n"); printf("5.insert an item 6.delete an item\n"); printf("7.delete all items 8.save file\n"); printf("9.search by name 10.quit\n"); int input = input_int(); if (input >= 1 && input <= 10) return input; else printf("%d is invalid. please try again\n", input); } } void print_all(struct movie movie_list[], int n_items) { for (int n = 0; n_items; ++n) printf("%d: \"%s\", %.1f\n", n, movie_list[n].title, movie_list[n].rating); } void print_an_item(struct movie movie_list[], int n_items) { printf("Input the index of item to print\n"); int index = input_int(); if (index < n_items) printf("%d: \"%s\", %.1f\n", index, movie_list[index].title, movie_list[index].rating); else printf("invalid items\n"); } void edit_an_item(struct movie movie_list[], int n_items) { printf(" 수정하기 위한 아이템의 인덱스를 입력하세요"); int index = input_int(); if (index < n_items) { printf("%d: \"%s\", %.1f\n", index, movie_list[index].title, movie_list[index].rating); printf("새 타이틀 입력후 엔터 쳐주세요"); printf(">>"); int f = scanf("%[^\n]%*c", movie_list[index].title); printf("새 평점 입력후 엔터 쳐주세요"); printf(">>"); f = scanf_s("%f%*c", &movie_list[index].rating); printf("%d: \"%s\", %.1f\n", index, movie_list[index].title, movie_list[index].rating); } else printf("invlaid items\n"); } void add_an_item(struct movie movie_list[], int* ptr_n_items)//n_items is a pointer { if (*ptr_n_items == LMAX) { printf("NO more space\n"); return; } const int index = *ptr_n_items; printf("타이틀 입력후 엔터\n"); printf(">>"); int f = scanf("%[^\n]%*c", movie_list[index].title); printf("평점 입력후 엔터\n"); printf(">>"); f = scanf("%f%*c", &movie_list[index].rating); printf("%d: \"%s\", %.1f\n", index, movie_list[index].title, movie_list[index].rating); *ptr_n_items += 1; } void insert_an_item(struct movie movie_list[], int* ptr_n_items) { if (*ptr_n_items == LMAX) { printf("공간 없음"); return; } printf("아이템 인덱스 입력"); int index = input_int(); //memmove(&movie_list[index+1], &movie_list[index], //sizeof(struct movie) * (*ptr_n_items -index)); /*for llop implemetation*/ for (int i = *ptr_n_items - 1; i >= index; i--) { strcpy(movie_list[i + 1].title, movie_list[i].title); movie_list[i + 1].rating = movie_list[i].rating; } //뒤에서 부터 한칸씩 앞으로 떙기는 거 printf("타이틀을 입력후 엔터 쳐주세요"); printf(">>"); int f = scanf("%[^\n]%*c", movie_list[index].title); printf("새 평점 입력후 엔터 쳐주세요"); printf(">>"); f = scanf("%f%*c", &movie_list[index].rating); printf("%d: \"%s\", %.1f\n", index, movie_list[index].title, movie_list[index].rating); *ptr_n_items += 1; } void delete_an_item(struct movie movie_list[], int* ptr_n_items) { printf("아이템 인덱스 입력"); int index = input_int(); //memmove(&movie_list[index+1], &movie_list[index], //sizeof(struct movie) * (*ptr_n_items -index)); /*for llop implemetation*/ for (int i = index; i < *ptr_n_items; i++) { strcpy(movie_list[i].title, movie_list[i + 1].title); movie_list[i].rating = movie_list[i + 1].rating; } *ptr_n_items -= 1; } void search_by_name(struct movie movie_list[], int n_items) { printf("찾으려는 타이틀 입력"); printf(">> "); char title[TSIZE] = { 0, }; if (scanf("%[^\n]%*c", title) != 1) { printf("Wrong input\n"); return; } int index = 0; for (; index < n_items; ++index) { if (strcmp(movie_list[index].title, title) == 0) break; } if (index == n_items) printf("영화를 찾을 수 없읍니다 :%s\n", title); else printf("%d: \"%s\", %.1f\n", index, movie_list[index].title, movie_list[index].rating); } int main() { struct movie movie_list[LMAX]; size_t n_items = 0; read_file(movie_list, &n_items); while (1) { printf("\n"); int s = input_menu(); switch (s) { case 1: print_all(movie_list, n_items); break; case 2: print_an_item(movie_list, n_items); break; case 3: edit_an_item(movie_list, n_items); break; case 4: add_an_item(movie_list, &n_items); break; case 5: insert_an_item(movie_list, &n_items); break; case 6: delete_an_item(movie_list, &n_items); break; case 7: n_items = 0; break; //& 있는애 있고 없는 애 있는데(n_items에서) 아이템 하나 추가 도ㅟ니까 값이 변해야 되므로 주솔르 넘겨준느 거. case 8: write_file(movie_list, n_items); break; case 9: search_by_name(movie_list, n_items); break; case 10: printf("Good bye\n"); exit(0); default: printf("%d is not implemented.\n", s); } } return 0; } 소스는 이렇게 다 따라 쳤는데 1번 실행하면 저렇게 에러가 뜨고 글자가 다 깨진 상태로 나오더라구요.. 이유를 알 수 있을까요?