Câu hỏi về node trong C

#include<stdio.h>
struct Node {
		int data;
		Node *next;
	};

void printf(Node *head) {
	int i=1;
	printf("----------------------------------\n");
	for (Node *cur = head; cur != NULL; cur = cur->next) {
		printf("Nut thu %d co gia tri la: %d\n",i, cur->data);
		i++;
	}
}
Node *Del_head(Node *head) {
	Node *del = head;
	head = head->next;
	free(del);
	return head;
}

int main() {
	int n;
	printf("Nhap so luong nut: n = ");scanf("%d",&n);
	Node *head, *tail, *newNode;
for (int i=1; i<=n; i++) {
		newNode = (Node*)malloc(sizeof(Node));
		scanf("%d", &newNode->data);
		if (i == 1) {
			head = newNode;
			tail = newNode;
		}
		else {
			tail->next = newNode;
			tail = newNode;
		}
	}
	tail->next = NULL;
printf(Del_head(head)); // printf(head = Del_head(head));
printf("\n%d\n", head->data);
return 0;
}

Anh chị cho em hỏi là đoạn code trên dùng để nhập vào giá trị của n node và xóa node đầu tiên của danh sách liên kết, nhưng khi em in ra giá trị của node đầu tiên sau khi xóa thì nó lại hiển thị ra 1 giá trị xa lạ ạ, còn khi em thay dòng code “printf(Del_head(head))” trong bài trên bằng dòng ở dấu gạch chéo 1 bên thì lại ra được kết quả đúng. Nhờ anh chị giải đáp giúp em với ạ.

Muốn thay đổi giá trị của con trỏ thì phải dùng con trỏ cấp 2 hoặc 3, 4, … :v

head trong hàm của bạn không thay đổi nên sau khi free nó sẽ là giá trị rác, còn khi bạn gán head từ giá trị trả về thì nó mới thay đổi bên ngoài hàm.

Ngoài ra thì, printf thiếu format string r kìa. :v

5 Likes

Trong hàm Del_head của em thì em có gán con trỏ head = con trỏ head->next nên con trỏ head phải trỏ sang nút thứ 2 chứ ạ, nên sau khi em gọi hàm xong thì con trỏ head vẫn phải trỏ về nút thứ 2 chứ ạ, còn phần printf thì là do em có viết 1 hàm ở trên cũng có tên là printf để in ra giá trị các nút ạ

Nó có trỏ sang nút tiếp theo, nhưng chỉ trong nội bộ hàm đó, biến head ngoài hàm và head trong hàm là 2 biến khác nhau, nhưng cùng lưu một giá trị (là địa chỉ của Node được cấp phát).

Thử hỏi, nếu truyền vào trong hàm mà vẫn thay đổi được giá trị thì ta cần con trỏ làm gì nữa?

3 Likes

Em vẫn không hiểu tại sao hai biến head đó lại khác nhau ạ, em gọi hàm Del_head(head) thì biến head ở ngoài hàm được truyền vào trong hàm để thực hiện thì 2 biến phải là như nhau chứ ạ, biến head đc truyền vào hàm để thực hiện lệnh thì khi thay đổi biến head ở trong hàm thì giá trị của nó sau khi hàm thực hiện xong cũng sẽ thay đổi chứ ạ. Còn cái mà 2 biến khác nhau thì em hiểu là VD trong 1 khối lệnh lớn ta khai báo biến a, sau đó ta lại khai báo 1 biến a trong khối lệnh nhỏ hơn đc chứa trong khối lệnh lớn đó thì 2 biến đó là 2 biến khác nhau ạ.

1 Like

Vậy là bị hổng kiến thức phần hàm rồi.

3 Likes

Vì C chỉ có cái gọi là pass by value. :v

Vậy bạn thử nói mình nghe đoạn code dưới chạy ra gì, và tại sao lại vậy đc k?

void func1(int x) {
  x += 1001;
  printf("%s: x = %d\n", __func__, x);
  printf("%s: pointer = %p\n", __func__, &x);
}

void func2(int *p_x) {
  *p_x += 1001;
  printf("%s: x = %d\n", __func__, *p_x);
  printf("%s: pointer = %p\n", __func__, p_x);
}

void func3(int *p) {
  p += 1001;
  printf("%s: pointer = %p\n", __func__, p);
  printf("%s: pointer 2 = %p\n", __func__, &p);
}

int main() {
  int x = 0;
  int *p_x = &x;
  printf("%s: x = %d\n", __func__, x);
  printf("%s: pointer = %p\n", __func__, p_x);

  func1(x);
  printf("%s: x = %d\n", __func__, x);
  printf("%s: pointer = %p\n", __func__, p_x);

  func2(p_x);
  printf("%s: x = %d\n", __func__, x);
  printf("%s: pointer = %p\n", __func__, p_x);

  func3(p_x);
  printf("%s: x = %d\n", __func__, x);
  printf("%s: pointer = %p\n", __func__, p_x);
  printf("%s: pointer 2 = %p\n", __func__, &p_x);
}
3 Likes

func đó là cái gì vậy ạ

Em làm đến cái đoạn func1(x) xong rồi mà sau đó với câu lệnh tiếp theo là in ra giá trị của x thì em lại phân vân giữa 0 với 1001 ạ, em nghĩ là em bị hơi bị rối cái phần này của hàm, mong anh/chị có thể giải thích thêm cho em với ạ

__func__ là macro cho tên hàm hiện tại. :v
Chưa nghĩ ra kết quả thì chạy code cũng được. Miễn sao bạn nhìn vào kết quả và hiểu sao nó lại ra như v là được.

4 Likes

Em hiểu r ạ, tức là khi gọi hàm thì mình chỉ truyền cái giá trị của biến, còn nếu muốn thay đổi thì phải thông qua con trỏ phải ko ạ. À còn điều nữa em thắc mắc nãy h ko bt xưng hô sao cho phù hợp là anh/chị là anh hay chị đó ạ :vvv. À còn cái pointer 2 đó là con trỏ cấp 2 phải ko ạ?

Đúng hướng r đó.


Xưng hô ngang hàng mình-bạn cũng đc. :v
Lib sempai bảo như này: :stuck_out_tongue:

xưng hô tớ-cậu là được rồi, vì ngoài tuổi ra tớ cũng chưa chắc hơn cậu cái gì

Btw, mình là nam. :v :V

6 Likes
83% thành viên diễn đàn không hỏi bài tập, còn bạn thì sao?