PDA

View Full Version : C and pointers



StOoZ
April 4th, 2009, 02:57 PM
Hi,
I just wonder , why I get weird characters when using 'studentReturn' , and good output when using the 'first' pointer.

the problem is in the lines :


studentReturn.first = (List*) malloc ( sizeof(List) );
studentReturn.first->head = first;
studentReturn.grade = ConvArrayToDec( grade , counter );


The Code is :

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

/************* structs***********************/
typedef struct list_node {

char* dataPtr;
struct list_node* next;

}ListNode;

typedef struct list {

ListNode* head;
ListNode* tail;

}List;

typedef struct student {

List* first;
int grade;

} Student;


/********************************************/

/* just to ease the creation of the linked list. */
/* this funtion creates a linked list from the stdin stream*/
List createScrabledList();
/* Prints the contents of a List */
void PrintList( List );
/* unscrable the list */
Student unScrable( List );
/* converts array of digits to a decimal number */
int ConvArrayToDec( int* , int );

void main() {

List lst;
Student std;

lst = createScrabledList();
printf("the scrambled list is :\n");
PrintList( lst );
printf("\n");
fflush(stdout);
std = unScrable( lst );

while ( std.first->head != NULL ) {

printf("%s" , std.first->head->dataPtr );
std.first->head = std.first->head->next;

}
printf("\nthe grade is %d", std.grade );

}



List createScrabledList() {

List* pList = (List*) malloc( sizeof(List) );
ListNode* node = NULL;

int ch;

while ( ( ch = getchar() ) != '\n' ) {

if ( NULL == node ) {
node = (ListNode*) malloc( sizeof(ListNode) );
node->dataPtr = (char*) malloc( sizeof(char) );
node->dataPtr[0] = ch;
pList->head = node;
} else {
node->next = (ListNode*) malloc( sizeof(ListNode) );
node = node->next;
node->dataPtr = (char*) malloc( sizeof(char) );
node->dataPtr[0] = ch;

}
}

node->next = NULL;

return *pList;

}


void PrintList( List lst ) {

while ( lst.head != NULL ) {

printf("%s", lst.head->dataPtr );
lst.head = lst.head->next;

}

}

int ConvArrayToDec( int* arr , int sz ) {

int num = 0 , i;
int numSqrt;
numSqrt = pow( 10 , sz - 1 );

for ( i = 0 ; i < sz ; i++ ) {

num += ( arr[i] * numSqrt );
numSqrt /= 10;

}
return num;
}


Student unScrable( List lst ) {

int grade[3] = {-1,-1,-1}; // assuming the avg can be 100.
int counter = 0;
ListNode* pTemp = NULL;
ListNode* pToFreeNode = NULL;
ListNode* first = lst.head;
Student studentReturn = { NULL , 0 };



while ( lst.head != NULL ) {

if ( isdigit(lst.head->dataPtr[0]) != 0 ) {

pTemp = lst.head;
while ( isdigit(pTemp->dataPtr[0]) != 0 ) {

pToFreeNode = pTemp;
grade[counter++] = (pTemp->dataPtr[0] - '0') ;
pTemp = pTemp->next;
free(pToFreeNode); // erasing the no-longer needed node.

}
*(lst.head) = *pTemp;
}

lst.head = lst.head->next;
}

// for debugging
/*
while ( first != NULL ) {

printf("%s" , first->dataPtr );
first = first->next;


}
*/
studentReturn.first = (List*) malloc ( sizeof(List) );
studentReturn.first->head = first;
studentReturn.grade = ConvArrayToDec( grade , counter );
return studentReturn;
}


when I use the commented code (under debugging) , all seems fine , the numbers are omitted and only the text appears , when I use it with the studentReturn structure , it doesnt work well , weired characters are displayed instead of the numbers that should not be displayed.

thanks!

Arndt
April 4th, 2009, 03:07 PM
Hi,
I just wonder , why I get weird characters when using 'studentReturn' , and good output when using the 'first' pointer.

the problem is in the lines :


studentReturn.first = (List*) malloc ( sizeof(List) );
studentReturn.first->head = first;
studentReturn.grade = ConvArrayToDec( grade , counter );


when I use the commented code (under debugging) , all seems fine , the numbers are omitted and only the text appears , when I use it with the studentReturn structure , it doesnt work well , weired characters are displayed instead of the numbers that should not be displayed.

thanks!

I haven't studied the code closely, and what I'm remarking on may not be the cause of the bug, but I find it odd to pass a whole structure by value, in for example the unScrable function:


Student unScrable( List lst ) {

I would use a declaration like this:


Student *unScrable( List *lst ) {

(and change the body and callers accordingly, of course).

StOoZ
April 4th, 2009, 03:24 PM
I know , but this is what I was asked to do according to the question's rules.

this is not the cause of the problem.
im still trying to figure out what can cause this problem.

thanks anyway.

nvteighen
April 4th, 2009, 05:08 PM
It segfaults for me at line 140.

I really don't understand what the hell (excuse me) are you trying to accomplish. Could you please explain us what your program is meant to do?

Can+~
April 4th, 2009, 05:41 PM
There are many weird things about this code, for instance



List* createScrabledList() {

List* pList = (List*) malloc( sizeof(List) );
ListNode* node = NULL;

int ch;

while ( ( ch = getchar() ) != '\n' ) {

if ( NULL == node ) {
node = (ListNode*) malloc( sizeof(ListNode) );
node->dataPtr = (char*) malloc( sizeof(char) );
node->dataPtr[0] = ch;
pList->head = node;
} else {
node->next = (ListNode*) malloc( sizeof(ListNode) );
node = node->next;
node->dataPtr = (char*) malloc( sizeof(char) );
node->dataPtr[0] = ch;

}
}

node->next = NULL;
plist->tail = node;

return *pList;

}

Why are you malloc'ing a character? You could use a plain char and stored the value there. (In bold)

You never updated the *tail of the base list (Added on red).

And the function is returning a list* instead of a list (Added on red) (Deleted on Green).

Function unScrabble and ConvArrayToDec are really hard to get what's going in there without any comments (and without any clear objective).

lloyd_b
April 5th, 2009, 01:29 AM
Another point that is probably part of the problem:
void PrintList( List lst ) {

while ( lst.head != NULL ) {

printf("%s", lst.head->dataPtr );
lst.head = lst.head->next;

}

}lst.head->dataPtr points to a single character, but the "%s" format expects a zero terminated character string.

Lloyd B.

majamba
April 5th, 2009, 01:41 AM
just use cpp and classes

unless this is c program required by your instructor i wondering why are you returning a value structure just passed as a pointer and change it.

not really familar with c, i have to look your code and see

http://www.ehow.com/how_2056292_create-linked-list-c.html

nvteighen
April 5th, 2009, 01:00 PM
just use cpp and classes

unless this is c program required by your instructor i wondering why are you returning a value structure just passed as a pointer and change it.

not really familar with c, i have to look your code and see

http://www.ehow.com/how_2056292_create-linked-list-c.html
Not necessarily: you can use C for OOP... the issue is that the program doesn't make any sense.