We help IT Professionals succeed at work.

returning to the head of linked list

nglp
nglp asked
on
632 Views
Last Modified: 2013-12-14
can anyone tell me the easiest way to go back to the head of the linked list at the end of the code below? i dun wish to add anything inside my struct unless i really have no choice.

inside my struct, i have a pointer
pointing to the nextPtr

thanks in advance!


ctr = 0;
if(*startPtr != NULL)
{
  while(*startPtr != NULL)
  {
    if(some condition)      
    {
      //delete one node from list
      //only enter here once
    }      
  (*startPtr) = (*startPtr)->nextPtr;
  ctr++;
  }
}
//go back to the head of the linked list before printing the linked list, else the list would be empty.

Comment
Watch Question

Commented:
All you need is an extra pointer (let's call it tempPtr) to the struct where you save startPtr in the begining (after ctr=0; do tempPtr=startPtr;) .
When you finish, all you need to do is: startPtr=tempPtr;.
This will not add fields to your struct, just use another pointer.

Hope this helps,
Arnon David.
Just to add to arnond's comment/answer:

Usually when you manage linked lists you need to keep a pointer to the head of the list. How do you intend to free the dynamically allocated elements anyway?

arnond's comment suggests that - but I assume you must have a pointer to the head of the list stored somewhere in the source code.

Author

Commented:
what i did is

NODEPTR *tmpPtr = NULL;
tmpPtr = startPtr;
.........

startPtr = tmpPtr;


but then when i printed, the list is empty too.  the tmpPtr pointer also increments to the tail of the list just like the startPtr.  What went wrong??

i also tried
NODEPTR tmpPtr = *startPtr;
but the program has some error and stop running....


Commented:
what went wrong is:
strPtr is a NODEPTR but tmpPtr as declared is a pointer to NODEPTR and therefore, tmpPtr will point to startPtr.
You should declare tmpPtr as:
NODEPTR tmpPtr = startPtr;

Arnon David.

Author

Commented:
arnond:

i tried that before, but there's compiling error which says
'=': cannot convert from 'struct Node **' to 'struct Node *'

Commented:
how did you declare startPtr ?

can you post your entire code here ar anywhere we can download it from ?
either that or post your e-mail and I'll send you an e-mail so that you can send me the file.

Arnon

Commented:
how did you declare startPtr ?

can you post your entire code here ar anywhere we can download it from ?
either that or post your e-mail and I'll send you an e-mail so that you can send me the file.

Arnon

Author

Commented:
Adjusted points to 100

Author

Commented:
arnond: the entire code is very long, so i paste the relevant parts below.  why not u 'answer' the question, so that i can give u the points.


struct listNode
{
      int level1[3][5];
      int level[3][5];
      int var1;
      int var2;
      float var3;
      float var4;
      struct listNode *nextPtr;
};
typedef struct listNode LISTNODE;
typedef LISTNODE *LISTNODEPTR;

main()
{
      LISTNODEPTR startPtr = NULL;
      LISTNODEPTR closePtr = NULL;                        
      LISTNODEPTR tempPtr = NULL;
      LISTNODEPTR tmpPtr = NULL;
      insert_node(&startPtr);      
      tempPtr = startPtr;      
……..

tmpPtr = agenda(&tempPtr,&closePtr,method);
………..
}

LISTNODEPTR pop_agenda(LISTNODEPTR *startPtr,LISTNODEPTR *closePtr,int method)
{
      LISTNODEPTR *tmpPtr2 = NULL;
      LISTNODEPTR leastcostPtr = NULL;
      ……………….

      tmpPtr2 = startPtr;
      ctr = 0;
      if(*startPtr != NULL)
      {
            while(*startPtr != NULL)
            {
                  if(selectctr == ctr)      
                  {
                  add_node(closePtr,level,level1, *startPtr)->var1*startPtr)->var2,(*startPtr)->var3*startPtr)->var4);
                        add_node(&leastcostPtr,level,level1,(*startPtr)->var1*startPtr)->var2,(*startPtr)->var3*startPtr)->var4);
                        delete_node(startPtr,level1,(*startPtr)->var1,(*startPtr)->var3,(*startPtr)->var4);
                  }
                  (*startPtr) = (*startPtr)->nextPtr;
                  ctr++;
            }
      }
      startPtr = tmpPtr2;


      return (leastcostPtr);
}

Commented:
did my previous comments 'answer' you question or do you need more help ? If it was enough you can just click the 'accept comment as answer' button on the relevant comment. If not, please let me know and I'll look at the code more closely.

Arnon David.

Author

Commented:
u said to
NODEPTR tmpPtr = startPtr;

but i have the compiling error which i mentioned before. can u help me look at the code?  thanks a great deal :)

Commented:
the only thing I'm not sure about is :
typedef LISTNODE *LISTNODEPTR;

I'd try to not use the typedef and just ust LISTNODE* instead.
Prehaps it should be:
typedef LISTNODE* LISTNODEPTR;
note the difference of the position of the '*'.

Arnon.

Commented:
LISTNODEPTR pop_agenda(LISTNODEPTR *startPtr,LISTNODEPTR *closePtr,int method)
{
LISTNODEPTR tmpPtr2 = NULL;
LISTNODEPTR leastcostPtr = NULL;
……………….

tmpPtr2 = *startPtr;
ctr = 0;
if(*startPtr != NULL)
{
while(*startPtr != NULL)
{
if(selectctr == ctr)
{
add_node(closePtr,level,level1, *startPtr)->var1*startPtr)->var2,(*startPtr)->var3*startPtr)->var4);
add_node(&leastcostPtr,level,level1,(*startPtr)->var1*startPtr)->var2,(*startPtr)->var3*startPtr)->var4);
delete_node(startPtr,level1,(*startPtr)->var1,(*startPtr)->var3,(*startPtr)->var4);
}
(*startPtr) = (*startPtr)->nextPtr;
ctr++;
}
}
*startPtr = tmpPtr2;


return (leastcostPtr);
}


You are getting confused with pointer pointers :) Change the function to this version and I think it should work. I changed the following lines:

LISTNODEPTR tmpPtr2 = NULL;


tmpPtr2 = *startPtr;


*startPtr = tmpPtr2;

Commented:
A little more info:

In your version, the last line does nothing:

startPtr = tmpPtr2;

because arguments are passed by value. The value in the calling function is not altered. That's a reason for passing pointers as arguments.

In your code you modify the start pointer like this:

*startPtr = whatever

but when you set it back, you have:

startPtr = tmpPtr2;

You need to dereference the pointer here to set the start pointer back.

For next time, its usually a good idea to have a pointer to the head of the list as part of the list struct. If you store a pointer to the end as well, additions are much faster because you dont have to iterate through the list to find the end.

Hi, nglp:

May I have a look at your function

insert_node(&startPtr);

According to your sample code, startPtr is a LISTNODEPTR.  Usually, we may use insert_node(startPtr) or insert_node(*startPtr).  But in your code, your insert the address of the pointer into the list.  Then, you should take care with your get_node(), delete_node, and othe functions.

tao_shaobin

Author

Commented:
okay, seems like it's very messy here... why not i restate my question?
i add an additional backPtr to my struct.  how do i amend the insert function below so that i can go the head of the list using

while(tmpPtr!=NULL)
{
tmpPtr=tmpPtr->backPtr;
}

p/s:thanks to all who commented.. but I really need to get this working with the least changes to the rest of my functions. thanks a million.


void insert(LISTNODEPTR *sPtr, char value)
{
      LISTNODEPTR newPtr, pregviousPtr,currentPtr;

      newPtr = malloc(sizeof(LISTNODE));

      if(newPtr != NULL)
      {
            newPtr->data = value;
            newPtr->nextPtr = NULL;

            previousPtr = NULL;
            currentPtr = *sPtr;

            while(currentPtr != NULL && value>currentPtr->data)
            {
                  previousPtr = currentPtr;
                  currentPtr = currentPtr->nextPtr;
            }

            if(previousPtr == NULL)
            {
                  newPtr->nextPtr = *sPtr;
                  *sPtr = newPtr;
            }
            else
            {
                  previousPtr->nextPtr = newPtr;
                  newPtr->nextPtr = currentPtr;
            }
      }
      else
            printf("%c not inserted.  No memory available. ",value);
}

Author

Commented:
I missed out on my last comment,take that my struct is of the form:
 
struct listNode
{
      char data;
      struct listNode *nextPtr;
};
typedef struct listNode LISTNODE;
typedef LISTNODE *LISTNODEPTR;
Commented:
This one is on us!
(Get your first solution completely free - no credit card required)
UNLOCK SOLUTION
Unlock the solution to this question.
Join our community and discover your potential

Experts Exchange is the only place where you can interact directly with leading experts in the technology field. Become a member today and access the collective knowledge of thousands of technology experts.

*This site is protected by reCAPTCHA and the Google Privacy Policy and Terms of Service apply.

OR

Please enter a first name

Please enter a last name

8+ characters (letters, numbers, and a symbol)

By clicking, you agree to the Terms of Use and Privacy Policy.