Remove the first element from link list in C - c

I'm having difficulty removing the first element from a Link List in C.
#include <stdio.h>
#include <stdlib.h>
typedef struct node {
int data;
struct node *next;
} node;
typedef struct list {
struct node *head;
} linklist;
void insertElement(linklist *list, node* curr);
void removeStart(node *curr);
int main(void){
int i;
node *curr;
linklist *list;
list = (linklist*)malloc(sizeof(linklist)); /* create head node */
list->head = NULL;
for(i=0; i<4; i++){
curr = (node*)malloc(sizeof(node));
curr->data = i;
curr->next = list->head; /* insert element to start */
list->head = curr; /* " " */
}
curr = list->head; /* traverse link list to start */
insertElement(list, curr);
curr = list->head;
removeStart(curr);
curr = list->head;
while(curr != NULL)
{
printf("%d\n", curr->data);
curr = curr->next;
}
return 0;
}
void insertElement(linklist *list, node *curr){
curr = (node*)malloc(sizeof(node));
curr->data = 4;
curr->next = list->head;
list->head = curr;
}
void removeStart(node *curr){
node *tmp;
tmp = curr;
curr = curr->next;
free(tmp);
}
When the code is compiled the final result should be:
3
2
1
0
Could someone please offer some suggestions on how I should go about this, also seperately how could a set it up to also remove any of the nodes in the link list. Thanks.

Try the following. At least the output coincides with the output you showed.
#include <stdio.h>
#include <stdlib.h>
typedef struct node
{
int data;
struct node *next;
} node;
typedef struct list
{
struct node *head;
} linklist;
void insertElement( linklist *list, int value )
{
node *tmp = malloc( sizeof( node ) );
tmp->data = value;
tmp->next = list->head;
list->head = tmp;
}
void removeStart( linklist *list )
{
if ( list != NULL && list->head != NULL )
{
node *tmp = list->head;
list->head = list->head->next;
free( tmp );
}
}
int main(void)
{
int i;
node *tmp;
linklist list;
list.head = NULL;
for ( i = 0; i < 4; i++ ) insertElement( &list, i );
insertElement( &list, i );
removeStart( &list );
for ( tmp = list.head; tmp != NULL; tmp = tmp->next )
{
printf( "%d ", tmp->data );
}
for ( tmp = list.head; tmp != NULL; )
{
node *current = tmp;
tmp = tmp->next;
free( current );
}
return 0;
}
3 2 1 0

My solution:
#include <stdio.h>
#include <stdlib.h>
typedef struct node {
int data;
struct node *next;
} node;
typedef struct list {
struct node *head;
} linklist;
void insertElement(linklist *list, node* curr);
void removeStart(linklist *list);
int main(void){
int i;
node *curr;
linklist *list;
list = (linklist*)malloc(sizeof(linklist)); /* create head node */
list->head = NULL;
for(i=0; i<4; i++){
curr = (node*)malloc(sizeof(node));
curr->data = i;
curr->next = list->head; /* insert element to start */
list->head = curr; /* " " */
}
curr = list->head; /* traverse link list to start */
insertElement(list, curr);
curr = list->head;
removeStart(list);
curr = list->head;
while(curr != NULL)
{
printf("%d\n", curr->data);
curr = curr->next;
}
return 0;
}
void insertElement(linklist *list, node *curr){
curr = (node*)malloc(sizeof(node));
curr->data = 4;
curr->next = list->head;
list->head = curr;
}
void removeStart(linklist *list){
node *tmp = NULL;
if(list->head != NULL)
{
tmp = list->head;
list->head = list->head->next;
}
free(tmp);
}

Related

Leetcode:Merge Two Sorted Lists. I don't know where the link is wrong

I would like to ask why this link list will not run the result. After running, it is TLE. I want the head to be an indicator, and the head list can be returned without modifying the head.
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* struct ListNode *next;
* };
*/
struct ListNode* mergeTwoLists(struct ListNode* list1, struct ListNode* list2){
if(!list1 && !list2) return NULL;
struct ListNode *head;
struct ListNode *node = head;
while(list1 && list2){
if(list1->val < list2->val){
node->next = list1;
list1 = list1->next;
node = node->next;
}
else{
node->next = list2;
list2 = list2->next;
node = node->next;
}
}
if(list1){
while(list1){
node->next = list1;
list1 = list1->next;
node = node->next;
}
}
if(list2){
while(list2){
node->next = list2;
list2 = list2->next;
node = node->next;
}
}
return head->next;
}
The function has undefined behavior because the pointer head and correspondingly the pointer node are not initialized
struct ListNode *head;
struct ListNode *node = head;
while(list1 && list2){
if(list1->val < list2->val){
node->next = list1;
//...
To make this assignment correct
node->next = list1;
you need initially to define a dummy node and set the pointer node to the address of the node.
The while loops like this
while(list1){
node->next = list1;
list1 = list1->next;
node = node->next;
}
in fact are redundant. In fact it is enough to write
node->next = list1;
or
node->next = list2;
Also the function does not change the original pointers of the two lists passed to the function as arguments.
The function should be declared and defined the following way as shown in the demonstration program below.
#include <stdio.h>
#include <stdlib.h>
typedef struct ListNode
{
int val;
struct ListNode *next;
} ListNode;
void clear( ListNode **head )
{
while (*head)
{
ListNode *current = *head;
*head = ( *head )->next;
free( current );
}
}
size_t assign( ListNode **head, const int a[], size_t n )
{
clear( head );
size_t i = 0;
for (; i != n && ( *head = malloc( sizeof( ListNode ) ) ) != NULL; i++)
{
( *head )->val = a[i];
( *head )->next = NULL;
head = &( *head )->next;
}
return i;
}
FILE *display( const ListNode *const head, FILE *fp )
{
for (const ListNode *current = head; current != NULL; current = current->next)
{
fprintf( fp, "%d -> ", current->val );
}
fputs( "null", fp );
return fp;
}
struct ListNode *mergeTwoLists( struct ListNode **list1, struct ListNode **list2 )
{
struct ListNode *head = NULL;
struct ListNode **current = &head;
struct ListNode *head1 = *list1;
struct ListNode *head2 = *list2;
while ( head1 && head2 )
{
if ( head2->val < head1->val )
{
*current = head2;
head2 = head2->next;
}
else
{
*current = head1;
head1 = head1->next;
}
current = &( *current )->next;
}
if ( head1 )
{
*current = head1;
}
else if ( head2 )
{
*current = head2;
}
*list1 = NULL;
*list2 = NULL;
return head;
}
int main( void )
{
struct ListNode *head1 = NULL;
struct ListNode *head2 = NULL;
int a[] = { 0, 2, 4, 6, 8 };
assign( &head1, a, sizeof( a ) / sizeof( *a ) );
int b[] = { 1, 3, 5, 7, 9 };
assign( &head2, b, sizeof( b ) / sizeof( *b ) );
fputc( '\n', display( head1, stdout ) );
fputc( '\n', display( head2, stdout ) );
struct ListNode *head3 = mergeTwoLists( &head1, &head2 );
fputc( '\n', display( head3, stdout ) );
clear( &head3 );
}
The program output is
0 -> 2 -> 4 -> 6 -> 8 -> null
1 -> 3 -> 5 -> 7 -> 9 -> null
0 -> 1 -> 2 -> 3 -> 4 -> 5 -> 6 -> 7 -> 8 -> 9 -> null
#include <stdio.h>
#include <stdlib.h>
// A nested list node
struct ListNode
{
int val;
struct ListNode *next;
};
// Add a node
void add(struct ListNode ** head_ref, int new_val)
{
struct ListNode* new_node = (struct ListNode*) malloc(sizeof(struct ListNode));
new_node->val = new_val;
new_node->next = (*head_ref);
(*head_ref) = new_node;
}
// Merge nodes of linked list src into dest
void merge(struct ListNode *dest, struct ListNode **src)
{
struct ListNode *dest_curr = dest, *src_curr = *src;
struct ListNode *dest_next, *src_next;
// While there are available positions in dest
while (dest_curr != NULL && src_curr != NULL)
{
// Save next pointers
dest_next = dest_curr->next;
src_next = src_curr->next;
// Make src_curr as next of dest_curr
// Change next pointer of src_curr
src_curr->next = dest_next;
// Change next pointer of dest_curr
dest_curr->next = src_curr;
// Update current pointers for next iteration
dest_curr = dest_next;
src_curr = src_next;
}
// Update head pointer of second list
*src = src_curr;
}
// Print linked list
void print(struct ListNode *head)
{
struct ListNode *temp = head;
while (temp != NULL)
{
printf("%d ", temp->val);
temp = temp->next;
}
printf("\n");
}
int main()
{
struct ListNode *dest = NULL, *src = NULL;
add(&dest, 2);
add(&dest, 1);
printf("First List: ");
print(dest);
add(&src, 4);
add(&src, 3);
printf("Second List: ");
print(src);
merge(dest, &src);
printf("Merger Lists: ");
print(dest);
getchar();
return 0;
}
Output:
First List: 1 2
Second List: 3 4
Merger Lists: 1 3 2 4

Segment Fault - Linked List in C

I am creating a basic linked list in C but I am getting a segment fault when my add to back function is called in my test file. It seems to have a problem because the head of the list is NULL, but I don't see why this is an issue. When I use the cgdb tool, it tells me the error is occurring on the line: prev->next = new_node. I have attached the full code below, please let me know what I am not seeing to fix this.
header file
#ifndef LINKED_LIST_H
#define LINKED_LIST_H
typedef struct Node {
int data;
struct Node *next;
} Node;
Node *create_node(int data);
void free_list(Node *head);
void add_to_front(struct Node **head, int data);
void print_list(struct Node *head);
void reverse_list(struct Node **head);
void add_to_back(Node **head, int data);
#endif // LINKED_LIST_H
.c file
#include <stdio.h>
#include <stdlib.h>
#include "linked_list.h"
/* returns a new node whose data is set to DATA and next is set to NULL */
Node *create_node(int data) {
struct Node *new_node = malloc(sizeof(struct Node));
if (new_node == NULL) {
perror("Malloc failed\n");
}
new_node->data = data;
new_node->next = NULL;
return new_node;
}
/* Frees the list starting at HEAD */
void free_list(Node *head) {
while (head != NULL) {
Node *temp = head->next;
free(head);
head = temp;
}
}
/* Creates a new node whose data is set to DATA and adds it to the front of the
list pointed to by HEAD.
*/
void add_to_front(struct Node **head, int data) {
/* Check if the head is NULL to make sure that we do not dereference a NULL pointer
because that would result in a segfault */
if (head == NULL) return;
struct Node *new_node = create_node(data);
if (*head != NULL) {
/* The list is not empty */
/* The new node's next should point to the head */
new_node->next = *head;
}
/* We must set HEAD using the following line in order to change the original list */
*head = new_node;
/* The following line would not work because it would only change our local copy of HEAD */
/* head = new_node */
}
/* Prints out a linked list starting at HEAD */
void print_list(struct Node *head) {
struct Node *curr;
for (curr = head; curr != NULL; curr = curr->next) {
printf("%d->", curr->data);
}
printf("NULL\n");
}
/* Iteratively reverses a linked list whose first node is HEAD */
void reverse_list(struct Node **head) {
if (head == NULL || *head == NULL) {
return;
}
struct Node *curr = *head;
struct Node *next = (*head)->next;
curr->next = NULL;
while (next != NULL) {
struct Node *temp = next->next;
next->next = curr;
curr = next;
next = temp;
}
*head = curr;
}
/* Creates a new node with a data field set to DATA and adds the node
to the back of the list pointed to by HEAD */
void add_to_back(Node **head, int data) {
if (head == NULL || *head == NULL) {
return;
}
Node *new_node = create_node(data);
Node *prev;
for (Node *curr = *head; curr != NULL; curr = curr->next) {
prev = curr;
}
prev->next = new_node;
}
test file
#include <assert.h>
#include <stdio.h>
#include <stdlib.h>
#include "linked_list.h"
int main(int argc, char **argv) {
printf("Running tests...\n\n");
Node *head = NULL;
/*********** reverse_list test ***********/
reverse_list(&head);
for (int i = 0; i < 5; ++i) {
add_to_front(&head, i);
reverse_list(&head);
}
int expected_values[] = {3, 1, 0, 2, 4};
Node *curr = head;
for (int i = 0; i < 5; ++i) {
assert(curr->data == expected_values[i]);
curr = curr->next;
}
free_list(head);
printf("Congrats! You have passed the reverse_list test!\n\n");
/************ add_to_back test ***********/
Node *head_2 = NULL;
add_to_back(&head_2, 15);
add_to_back(&head_2, 12);
add_to_back(&head_2, 18);
int expected_values_2[] = {15, 12, 18};
Node *curr_2 = head_2;
for (int i = 0; i < 3; ++i) {
assert(curr_2->data == expected_values_2[i]);
curr_2 = curr_2->next;
}
free_list(head_2);
printf("Congrats! All of the test cases passed!\n");
return 0;
}
The if statement in the function add_to_back
if (head == NULL || *head == NULL) {
return;
}
does not make a sense because it does not allow to append a node to an empty list.
The function can be defined for example like
void add_to_back( Node **head, int data )
{
if ( head == NULL ) return;
Node *new_node = create_node(data);
while ( *head ) head = &( *head )->next;
*head = new_node;
}
Or using your approach then
void add_to_back( Node **head, int data )
{
if ( head == NULL ) return;
Node *new_node = create_node(data);
Node *prev = NULL;
for ( Node *curr = *head; curr != NULL; curr = curr->next )
{
prev = curr;
}
prev == NULL ? ( *head = new_node ) : ( prev->next = new_node );
}
In general this statement
if ( head == NULL ) return;
is also redundant. If the user will pass a null pointer then the function just will have undefined behavior.
On the other hand the function create_node should be written the following way
Node * create_node( int data )
{
struct Node *new_node = malloc(sizeof(struct Node));
if ( new_node != NULL )
{
new_node->data = data;
new_node->next = NULL;
}
return new_node;
}
Correspondingly for example the function add_to_back can be written like
int add_to_back( Node **head, int data )
{
Node *new_node = create_node( data );
int success = new_node != NULL;
if ( success )
{
Node *prev = NULL;
for ( Node *curr = *head; curr != NULL; curr = curr->next )
{
prev = curr;
}
prev == NULL ? ( *head = new_node ) : ( prev->next = new_node );
}
return success;
}
The problem is in the add_to_back() function. Because of first line in that function if (head == NULL || *head == NULL) { return; }, it will keep returning and not executing rest of the code. So, if you print your list after three calls of the add_to_back function, your list has nothing but NULL and that is the reason you are getting a segmentation fault. I did the following change and your code is working fine
`
void add_to_back(Node **head, int data) {
Node *new_node = create_node(data);
if (*head == NULL){
*head = new_node;
return;
}
Node *prev;
for (Node *curr = *head; curr != NULL; curr = curr->next) {
prev = curr;
}
prev->next = new_node;
}
`

Sorting a singly linked list with multiple elements in C [duplicate]

In C I have to write a bubble sort function that swaps the nodes and not the values of a LinkedList, but I'm unable to accomplish it. Here is the code (As you can see the order is not correct):
#include <stdio.h>
#include <malloc.h> // malloc, free
#include <stddef.h> // NULL
// defining 'int' as data_t
typedef int data_t;
typedef struct node_s {
data_t data;
struct node_s* next;
} node_t;
node_t** list_new() {
node_t** list = malloc(sizeof **list);
if (!list) return NULL;
*list = NULL;
return list;
}
void list_delete(node_t** list) {
node_t *node, *next;
for (node = *list; node; node = next) {
next = node->next;
free(node);
}
}
node_t* list_push_front(node_t** list, data_t data) {
node_t* node = malloc(sizeof(node_t));
if (!node) return NULL;
node->data = data;
node->next = *list;
return *list = node;
}
// IS EASY TO SWAP THE VALUES
/*
void swap(data_t* a, data_t* b) {
data_t c = *a;
*a = *b;
*b = c;
}
void simple_bubble_sort(node_t** list) {
for(node_t* i = *list; i; i = i->next)
for(node_t* j = *list; j->next; j = j->next)
if(j->data > j->next->data)
swap(&(j->data), &(j->next->data));
}
*/
// MUCH LESS EASY TO SWAP THE NODES
void swap_node(node_t** prev_node_A, node_t** node_A, node_t** node_B) {
node_t *last_node = (*node_B)->next;
node_t *first_node = *node_A;
node_t *second_node = *node_B;
if (prev_node_A) {
(*prev_node_A)->next = second_node;
(*prev_node_A)->next->next = first_node;
(*prev_node_A)->next->next->next = last_node;
} else {
(*node_A) = second_node;
(*node_A)->next = first_node;
(*node_A)->next->next = last_node;
}
}
void simple_bubble_sort(node_t** list) {
for(node_t* i = *list; i->next; i = i->next)
for (node_t *j = *list; j->next->next; j = j->next) {
if (j == *list) {
if (j->data > j->next->data) {
*list = j->next;
swap_node(NULL, &j, &(j->next));
}
}
else {
if (j->next->data > j->next->next->data)
swap_node(&j, &(j->next), &(j->next->next));
}
//printf("%i,%i | %i, %i, %i, %i \n", i->data, j->data, (*list)->data, (*list)->next->data, (*list)->next->next->data, (*list)->next->next->next->data);
//system("pause");
}
}
int main() {
// Create List
node_t** list = list_new();
if (!list)
goto memory_allocation_failure;
// Add values to List
for(int i=0; i<10; i++)
if (!list_push_front(list, i))
goto memory_allocation_failure;
// Print List
for (node_t* node = *list; node != NULL; node = node->next)
printf("%i\n", node->data);
// Swap Test
//swap_node(NULL, &(*list), &((*list)->next));
//swap_node(&(*list), &((*list)->next), &((*list)->next->next));
// Sort List
printf("-- Bubble Sort --\n");
simple_bubble_sort(list);
// Print List
for (node_t* node = *list; node != NULL; node = node->next)
printf("%i\n", node->data);
// Delete List
list_delete(list);
return 0;
// Error Handler
memory_allocation_failure:
printf("Memory Allocation Failure");
return 1;
}
Here is the function swap.
void swap( node_t **current )
{
node_t *tmp = ( *current )->next->next;
( *current )->next->next = *current;
*current = ( *current )->next;
( *current )->next->next = tmp;
}
And here is the function simple_bubble_sort
void simple_bubble_sort( node_t **head )
{
if ( *head )
{
for ( node_t **first = head, *sorted = NULL, *last = sorted;
( *first )->next != last;
last = sorted )
{
sorted = ( *first )->next;
for ( node_t **current = first; ( *current )->next != last; current = &( *current )->next )
{
if ( ( *current )->next->data < ( *current )->data )
{
swap( current );
sorted = ( *current )->next;
}
}
}
}
}
Investigate them.
Pay attention to that the header <malloc.h> is not a standard C header. Instead use the header <stdlib.h>.
You need to revise your current code. For example this function
node_t** list_new() {
node_t** list = malloc(sizeof **list);
if (!list) return NULL;
*list = NULL;
return list;
}
does not make sense it should be removed.
What you need is just to define in main a pointer like
node_t *head = NULL;
And pass it to functions as for example to the function simple_bubble_sort like
simple_bubble_sort( &head );
Or the function list_push_front should be defined like
int list_push_front(node_t** list, data_t data)
{
node_t* node = malloc(sizeof(node_t));
int success = node != NULL;
if ( success )
{
node->data = data;
node->next = *list;
*list = node;
}
return success;;
}

How do I swap the nodes of a linked list in a bubble-sort algorithm?

In C I have to write a bubble sort function that swaps the nodes and not the values of a LinkedList, but I'm unable to accomplish it. Here is the code (As you can see the order is not correct):
#include <stdio.h>
#include <malloc.h> // malloc, free
#include <stddef.h> // NULL
// defining 'int' as data_t
typedef int data_t;
typedef struct node_s {
data_t data;
struct node_s* next;
} node_t;
node_t** list_new() {
node_t** list = malloc(sizeof **list);
if (!list) return NULL;
*list = NULL;
return list;
}
void list_delete(node_t** list) {
node_t *node, *next;
for (node = *list; node; node = next) {
next = node->next;
free(node);
}
}
node_t* list_push_front(node_t** list, data_t data) {
node_t* node = malloc(sizeof(node_t));
if (!node) return NULL;
node->data = data;
node->next = *list;
return *list = node;
}
// IS EASY TO SWAP THE VALUES
/*
void swap(data_t* a, data_t* b) {
data_t c = *a;
*a = *b;
*b = c;
}
void simple_bubble_sort(node_t** list) {
for(node_t* i = *list; i; i = i->next)
for(node_t* j = *list; j->next; j = j->next)
if(j->data > j->next->data)
swap(&(j->data), &(j->next->data));
}
*/
// MUCH LESS EASY TO SWAP THE NODES
void swap_node(node_t** prev_node_A, node_t** node_A, node_t** node_B) {
node_t *last_node = (*node_B)->next;
node_t *first_node = *node_A;
node_t *second_node = *node_B;
if (prev_node_A) {
(*prev_node_A)->next = second_node;
(*prev_node_A)->next->next = first_node;
(*prev_node_A)->next->next->next = last_node;
} else {
(*node_A) = second_node;
(*node_A)->next = first_node;
(*node_A)->next->next = last_node;
}
}
void simple_bubble_sort(node_t** list) {
for(node_t* i = *list; i->next; i = i->next)
for (node_t *j = *list; j->next->next; j = j->next) {
if (j == *list) {
if (j->data > j->next->data) {
*list = j->next;
swap_node(NULL, &j, &(j->next));
}
}
else {
if (j->next->data > j->next->next->data)
swap_node(&j, &(j->next), &(j->next->next));
}
//printf("%i,%i | %i, %i, %i, %i \n", i->data, j->data, (*list)->data, (*list)->next->data, (*list)->next->next->data, (*list)->next->next->next->data);
//system("pause");
}
}
int main() {
// Create List
node_t** list = list_new();
if (!list)
goto memory_allocation_failure;
// Add values to List
for(int i=0; i<10; i++)
if (!list_push_front(list, i))
goto memory_allocation_failure;
// Print List
for (node_t* node = *list; node != NULL; node = node->next)
printf("%i\n", node->data);
// Swap Test
//swap_node(NULL, &(*list), &((*list)->next));
//swap_node(&(*list), &((*list)->next), &((*list)->next->next));
// Sort List
printf("-- Bubble Sort --\n");
simple_bubble_sort(list);
// Print List
for (node_t* node = *list; node != NULL; node = node->next)
printf("%i\n", node->data);
// Delete List
list_delete(list);
return 0;
// Error Handler
memory_allocation_failure:
printf("Memory Allocation Failure");
return 1;
}
Here is the function swap.
void swap( node_t **current )
{
node_t *tmp = ( *current )->next->next;
( *current )->next->next = *current;
*current = ( *current )->next;
( *current )->next->next = tmp;
}
And here is the function simple_bubble_sort
void simple_bubble_sort( node_t **head )
{
if ( *head )
{
for ( node_t **first = head, *sorted = NULL, *last = sorted;
( *first )->next != last;
last = sorted )
{
sorted = ( *first )->next;
for ( node_t **current = first; ( *current )->next != last; current = &( *current )->next )
{
if ( ( *current )->next->data < ( *current )->data )
{
swap( current );
sorted = ( *current )->next;
}
}
}
}
}
Investigate them.
Pay attention to that the header <malloc.h> is not a standard C header. Instead use the header <stdlib.h>.
You need to revise your current code. For example this function
node_t** list_new() {
node_t** list = malloc(sizeof **list);
if (!list) return NULL;
*list = NULL;
return list;
}
does not make sense it should be removed.
What you need is just to define in main a pointer like
node_t *head = NULL;
And pass it to functions as for example to the function simple_bubble_sort like
simple_bubble_sort( &head );
Or the function list_push_front should be defined like
int list_push_front(node_t** list, data_t data)
{
node_t* node = malloc(sizeof(node_t));
int success = node != NULL;
if ( success )
{
node->data = data;
node->next = *list;
*list = node;
}
return success;;
}

linked list c programming error by inserting new element

I am trying to insert an element but it get the error "Process finished with exit code 11"
struct node {
int key;
struct node *next;
};
struct node* init(){
struct node *head =NULL;
return head;
}
void create(struct node * head,int num) {
struct node * tmp = head;
struct node * prev = NULL;
struct node* new = malloc(sizeof(struct node));
new->key = num;
prev = tmp;
tmp = tmp->next;
while(tmp!= NULL && tmp->key < num){
prev = tmp;
tmp = tmp->next;
}
new->next = tmp;
prev->next = new;
if (tmp== NULL)
head=tmp;
}
int main() {
int num;
struct node* head;
head=init()
printf("Enter data:");
scanf("%d",&num);
create(head,num);
}
i am trying to insert an element into a linked list and the element should be sorted and entered at the same time.can someone tell me that the error is ? i cannot seem to find out the error.
It's not clear what your function create()
void create(struct node * head, int num) {
struct node * tmp = head;
struct node * prev = NULL;
struct node* new = malloc(sizeof(struct node));
new->key = num;
prev = tmp;
tmp = tmp->next;
while (tmp != NULL && tmp->key < num) {
prev = tmp;
tmp = tmp->next;
}
new->next = tmp;
prev->next = new;
if (tmp == NULL)
head = tmp;
}
is supposed to do. You effectively pass it a NULL pointer and return void, so everything it does is meaningless to the outside world.
Thetm starting point for every no bs linked list implementation:
#include <stdbool.h>
#include <stdlib.h>
#include <stdio.h>
typedef struct node_tag {
int value;
struct node_tag *next;
} node_t;
// write functions to encapsulate the data and provide a stable interface:
node_t* node_create_value(int value)
{
node_t *new_node = calloc(1, sizeof *new_node);
if(new_node) new_node->value = value;
return new_node;
}
node_t* node_advance(node_t const *node) { return node->next; }
typedef struct list_tag { // a list usually consists of
node_t *head; // a pointer to the first and
node_t *tail; // a pointer to the last element
// size_t size; // one might want to add that.
} list_t;
list_t list_create(void)
{
list_t list = { NULL, NULL };
return list;
}
// make code based on these functions "speak" for itself:
node_t* list_begin(list_t const *list) { return list->head; }
node_t* list_end (list_t const *list) { return list->tail; }
bool list_is_empty(list_t const *list) { return !list_begin(list); }
// common operations for lists:
node_t* list_push_front(list_t *list, int value)
{
node_t *new_node = node_create_value(value);
if (!new_node)
return NULL;
new_node->next = list->head;
return list->head = new_node;
}
node_t* list_push_back(list_t *list, int value)
{
// push_back on an empty list is push_front:
if (list_is_empty(list))
return list->tail = list_push_front(list, value);
node_t *new_node = node_create_value(value);
if (!new_node)
return NULL;
list->tail->next = new_node;
return list->tail = new_node;
}
node_t* list_insert_after(list_t *list, node_t *node, int value)
{
if (list_end(list) == node)
return list_push_back(list, value);
node_t *new_node = node_create_value(value);
if (!new_node)
return NULL;
new_node->next = node->next;
return node->next = new_node;
}
node_t* list_insert_sorted(list_t *list, int value)
{
// first handle the special cases that don't require iterating the whole list:
if (list_is_empty(list) || value < list_begin(list)->value)
return list_push_front(list, value);
if (value > list_end(list)->value)
return list_push_back(list, value);
// the general (worst) case:
for (node_t *current_node = list_begin(list); node_advance(current_node); current_node = node_advance(current_node))
if (value < node_advance(current_node)->value)
return list_insert_after(list, current_node, value);
return NULL; // should never happen
}
void list_print(list_t const *list)
{
for (node_t *current_node = list_begin(list); current_node; current_node = node_advance(current_node))
printf("%d\n", current_node->value);
}
void list_free(list_t *list)
{
for(node_t *current_node = list_begin(list), *next_node; current_node; current_node = next_node) {
next_node = current_node->next;
free(current_node);
}
}
// user code should not be required to know anything about the inner workings
// of our list:
int main(void)
{
list_t list = list_create();
for (int i = 1; i < 10; i += 2) {
if (!list_push_back(&list, i)) {
list_free(&list);
fputs("Not enough memory :(\n\n", stderr);
return EXIT_FAILURE;
}
}
list_print(&list);
putchar('\n');
for (int i = 0; i < 11; i += 2) {
if (!list_insert_sorted(&list, i)) {
list_free(&list);
fputs("Not enough memory :(\n\n", stderr);
return EXIT_FAILURE;
}
}
list_print(&list);
list_free(&list);
}
Output:
1
3
5
7
9
0
1
2
3
4
5
6
7
8
9
10

Resources