我编写了一个程序,该程序获得一些值并将其放入排序的链表中。 问题是输入第一个值后 程序停止 而且甚至没有运行插入功能
我知道问题出在将参数传递给insert函数 但是我不知道如何解决。
save
结果:
/用户/ Danial / CLionProjects /示例/ cmake-build-debug /示例 输入您的值3
进程以退出代码11完成
答案 0 :(得分:0)
在这里声明NULL
并将其设置为struct record *headptr = NULL;
:
insert
然后将其传递给insert(headptr, data);
:
ptr
因此,insert
中的NULL
是void insert(struct record *ptr, int value)
:
curptr = ptr;
然后,您设置curptr
,因此NULL
是while (value >= (curptr->data)) {
。然后它在此行崩溃:
curptr
因为您正在尝试访问NULL
所指向的内存,此时内存为headptr
。
我的猜测是,您想先将insert
的内存分配给NULL
。或者处理指针在insert
中为$ cat test-cm.yaml
apiVersion: v1
data:
key1: value1
key2: value2
"": value3
kind: ConfigMap
metadata:
name: test-cm
$ kubectl apply -f test-cm.yaml
The ConfigMap "test-cm" is invalid: data[]: Invalid value: "": a valid config key must consist of alphanumeric characters, '-', '_' or '.' (e.g. 'key.name', or 'KEY_NAME', or 'key-name', regex used for validation is '[-._a-zA-Z0-9]+')
$
的情况。
答案 1 :(得分:0)
如果将指针传递给函数,则尽管可以更改指针指向的内容,但不能修改指针,但要实现此目的,必须将指针传递给指针:
#include <stdio.h>
#include <stdlib.h>
struct record{
int data;
struct record *nextptr;
};
void insert (struct record** ptr, int value);
void printList(struct record *ptr);
int main() {
struct record *headptr = NULL;
for (int i = 0; i < 4; ++i) {
int data;
printf("Enter your value");
scanf("%d", &data);
insert(&headptr, data);
}
printList(headptr);
return 0;
}
void insert (struct record** ptr, int value) {
if ( ptr == NULL ) {
//Do nothing ptr is invalid
return;
}
printf("WE ARE IN THE INSERT FUNCTION");
struct record* curptr = *ptr
,* newptr = (struct record *) malloc(sizeof(struct record));
newptr->data = value;
//Check curptr isn't NULL
while(curptr != NULL && value >= (curptr->data)){
curptr = curptr->nextptr;
}
if (curptr == NULL) {
newptr->nextptr = NULL;
*ptr = newptr;
} else {
newptr->nextptr = curptr;
}
}
void printList(struct record *ptr){
while(ptr->nextptr != NULL) {
printf("%d", ptr->data);
ptr = ptr->nextptr;
}
}
答案 2 :(得分:0)
insert
有两个大问题。首先,您将ptr
作为指针struct record
传递。发生这种情况时,您的insert
函数会收到一个指针的副本,该指针指向内存中的相同位置,但自身具有不同的地址,与从main()
。这与您在insert
中对指针的副本所做的操作无关紧要,这些更改将永远不会在main()
中看到,因为您正在操作副本,而不会返回任何值。要解决该问题,请设置参数struct record **
并传递main()
中指针的地址。
您在insert
中遇到的下一个最大问题是,在开始之前,您无法检查curptr
是否为NULL
(因为它将是对insert
的第一次呼叫)开始取消对curptr
的引用-可能导致段错误或工厂的其他运行未定义行为。
创建链接列表时,必须满足两个不同的测试条件:
value
的{{1}}进行迭代以找到合适的2节点以在其中插入数据。您可以简单地处理这两种情况:
data
在您编写的分配内存的任何程序中,必须保留一个指向分配的每个块的开头的指针,以便在不再需要该内存时可以将其释放。通常,您将需要编写一个 rec_t *curptr = *ptr,
*newptr = malloc (sizeof *newptr);
if (!newptr) {
perror ("malloc-newptr");
return;
}
newptr->data = value;
newptr->nextptr = NULL;
if (curptr == NULL) { /* handle new-list case and return */
*ptr = newptr;
return;
}
if (value < curptr->data) { /* handle new 1st node */
newptr->nextptr = curptr;
*ptr = newptr;
return;
}
/* iterate with curptr until value > curptr->nextptr->data */
while (curptr->nextptr != NULL && value > curptr->nextptr->data)
curptr = curptr->nextptr;
newptr->nextptr = curptr->nextptr; /* wire new node to next node */
curptr->nextptr = newptr; /* wire current to new node */
函数来为您处理。您可以编写类似以下内容的简单内容:
listfree
(注意:在列表前进到下一个节点之前,如何将要释放的节点保存到临时指针void freelist (rec_t *head)
{
while (head) {
rec_t *victim = head;
head = head->nextptr;
free (victim);
}
}
中。)
完全将其放入,您可以执行以下操作:
victim
使用/输出示例
#include <stdio.h>
#include <stdlib.h>
typedef struct record {
int data;
struct record *nextptr;
} rec_t;
void insert (rec_t **ptr, int value);
void printList (rec_t *ptr);
void freelist (rec_t *head);
int main (void) {
rec_t *headptr = NULL;
for (int i = 0; i < 4; ++i) {
int data;
printf("Enter your value: ");
scanf("%d", &data);
insert (&headptr, data);
}
printList(headptr);
freelist (headptr);
return 0;
}
void insert (rec_t **ptr, int value)
{
if ( ptr == NULL ) {
return;
}
rec_t *curptr = *ptr,
*newptr = malloc (sizeof *newptr); /* don't cast the return */
if (!newptr) {
perror ("malloc-newptr");
return;
}
newptr->data = value;
newptr->nextptr = NULL;
if (curptr == NULL) { /* handle new-list case and return */
*ptr = newptr;
return;
}
if (value < curptr->data) { /* handle new 1st node */
newptr->nextptr = curptr;
*ptr = newptr;
return;
}
/* iterate with curptr until value > curptr->nextptr->data */
while (curptr->nextptr != NULL && value > curptr->nextptr->data)
curptr = curptr->nextptr;
newptr->nextptr = curptr->nextptr; /* wire new node to next node */
curptr->nextptr = newptr; /* wire current to new node */
}
void printList(struct record *ptr)
{
while (ptr != NULL) {
printf(" %d", ptr->data);
ptr = ptr->nextptr;
}
putchar ('\n');
}
void freelist (rec_t *head)
{
while (head) {
rec_t *victim = head;
head = head->nextptr;
free (victim);
}
}
仔细研究一下,如果您有任何疑问,请告诉我。
答案 3 :(得分:0)
首先,如果要在程序意外终止之前冲洗打印件,请使用setbuf(stdout, NULL);
。
第二,就像其他人提到的那样,您正在访问NULL
中的while (value >= (curptr->data))
指针元素,这会导致崩溃。
第三,您的insert
和print
逻辑也是错误的。
#include <stdio.h>
#include <stdlib.h>
struct record{
int data;
struct record *nextptr;
};
void insert (struct record **ptr,int value);
void printList(struct record *ptr);
int main() {
setbuf(stdout, NULL);
struct record *headptr = NULL;
for (int i = 0; i < 4; ++i) {
int data;
printf("Enter your value");
scanf("%d", &data);
insert(&headptr, data);
}
printList(headptr);
return 0;
}
void insert (struct record **head,int value){
printf("WE ARE IN THE INSERT FUNCTION");
struct record *newptr = (struct record *) malloc(sizeof(struct record));
newptr->data=value;
newptr->nextptr=NULL;
struct record *curptr=*head;
struct record *prevcurptr=NULL;
while(curptr!=NULL && value >= (curptr->data)){
prevcurptr=curptr;
curptr=curptr->nextptr;
}
if (curptr==NULL){
if (prevcurptr==NULL) {
*head=newptr;
} else {
newptr->nextptr=prevcurptr->nextptr;
prevcurptr->nextptr=newptr;
}
}
else{
newptr->nextptr=curptr;
if (prevcurptr==NULL)
*head=newptr;
else
prevcurptr->nextptr=newptr;
}
}
void printList(struct record *ptr){
while(ptr != NULL){
printf("\n %d", ptr->data);
ptr=ptr->nextptr;
}
}