HiveBrain v1.2.0
Get Started
← Back to all entries
patterncppMinor

Single Linked List - Improvements - 1 - not complete

Submitted by: @import:stackexchange-codereview··
0
Viewed 0 times
linkedcompletesinglelistimprovementsnot

Problem

TO DO

  • exception handling



  • merge with dynamic arrary



*SO Bug here--remove this line and Control K will not work

```
/*
Added in comments from Jerry, Ed and Loki
This code borrows from from http://cslibrary.stanford.edu/
C++ Version - lnode, lnode_reverse, lnode_push, lnode_print, lnode_count
*/
#include "c_arclib.cpp"
template class sl_list
{
private:
class node_1
{
public:
T1 data;
node_1 *next;
node_1(T1 data, node_1 *next = NULL) : data(data), next(next) {}
};
node_1 *head;
int count;
public:
sl_list() : count(0), head(NULL){}
void push(int data)
{
node_1 *newNode = new node_1(data, head);
++count;
head = newNode;
}
void print()
{
node_1 *current=head;
while (current != NULL)
{
cout data next;
}
}
void reverse()
{
node_1 previous, current, *future;
previous=NULL;
current=head;
future=head;
while(current!=NULL)
{
future=current->next;
current->next=previous;
previous=current;
current=future;
}
head=previous;
}
void break_heap()
{
int i=0;
while(1)
{
i++;
push(1);
}
}
};
/*
C Version - lnode, lnode_reverse, lnode_push, lnode_print, lnode_count
*/

typedef struct node_type
{
int data;
struct node_type* next;
} lnode_type;

struct lnode
{
int data;
struct lnode* next;
};
void lnode_reverse(struct lnode*& head)
{
struct lnode previous, current, *future;
previous=NULL;
current=head;
future=head;
while(current!=NULL)
{
future=current->next;
current->next=previous;
previous=current;
current=future;
}
head=previous;
}
void lnode_push(struct lnode*& head, int data)
{
struct lnode* newNode = new lnode;
newNode->data = data;
newNode->next = head;
head = newN

Solution

/* C++ Version - lnode, lnode_reverse, lnode_push, lnode_print, lnode_count
   I need node_type turned into a templated class..How does one do this?
*/
typedef struct node_type 
  { 
  int data; 
  struct node_type* next; 
  } lnode_type;


Turning it into a template is pretty straightforward:

template 
class node_type { 
   T data;
   node_type *next;
};


Note that the typedef isn't really necessary (or desirable) in C++. You normally just want to use class whatever, and then the body of the class definition. This makes whatever usable as a name by itself, just about like the typedef would in C.

There's one other thing we probably want to do though: the whole basic idea of a linked-list node is really just an implementation detail of the linked list, so we really want to make the node type a nested class inside of the linked-list class:

template 
class sl_list {

    struct node {
        T data;
        node *next;
    } head;

public:
    // Other stuff here.
};


From there, we want to write the functions that work with the data type to use T instead of int. For example, instead of your push(int), you might write something like this:

void push(T data) {
  ++count; // prefer pre-increment when you don't need the old value.
  node* newNode = new node; 
  newNode->data = data;
  newNode->next = head;
  head = newNode; 
}


We might prefer to add a ctor to the node class/struct, something like this:

node(T data, node *next = NULL) : data(data), next(next) {}


With that, push becomes something like this:

void push(T data) { 
    node *newNode = new node(data, head);
    ++count;
    head = newNode;
}


[Edit2: Note that, as recommended by @LokiAstari, I've also moved the ++count to after allocating the new node. This way if the attempted allocation fails (and new throws an exception), count will not be incremented, so it retains the correct values. If and only if the allocation succeeds, it's incremented to reflect the new node having been added to the list. ]

[Edit: and node would look roughly like this:

struct node {
        T data;
        node *next;

        node(T data, node *next = NULL) : data(data), next(next) {}            
    } head;


]

Code Snippets

/* C++ Version - lnode, lnode_reverse, lnode_push, lnode_print, lnode_count
   I need node_type turned into a templated class..How does one do this?
*/
typedef struct node_type 
  { 
  int data; 
  struct node_type* next; 
  } lnode_type;
template <class T>
class node_type { 
   T data;
   node_type *next;
};
template <class T>
class sl_list {

    struct node {
        T data;
        node *next;
    } head;

public:
    // Other stuff here.
};
void push(T data) {
  ++count; // prefer pre-increment when you don't need the old value.
  node* newNode = new node; 
  newNode->data = data;
  newNode->next = head;
  head = newNode; 
}
node(T data, node *next = NULL) : data(data), next(next) {}

Context

StackExchange Code Review Q#5724, answer score: 6

Revisions (0)

No revisions yet.