Question

My college professor taught us that a generic stack looks something like this (I basically copy-pasted this from the course support files):

typedef struct
{ size_t maxe, dime;  
  char *b, *sv, *vf;  
} TStiva, *ASt;

#define DIME(a) (((ASt)(a))->dime)
#define BS(a) (((ASt)(a))->b)
#define SV(a) (((ASt)(a))->sv)
#define VF(a) (((ASt)(a))->vf)
#define DIMDIF(s,d) (DIME(s) != DIME(d))
#define VIDA(a)  (VF(a) == BS(a))
#define PLINA(a) (VF(a) == SV(a))

// Function Declarations
void* InitS(size_t d,...);
int Push(void* a, void* ae);
int Pop (void* a, void* ae);
int Top (void* a, void* ae);

void *InitS(size_t d,...) 
{ ASt a = (ASt)malloc(sizeof (TStiva));
  va_list ap;
  if (!a) return NULL;
  va_start(ap,d);
  a->maxe = va_arg(ap,size_t);  
  va_end(ap);
  a->dime = d;
  a->b = (char*)calloc(a->maxe, d);         
  if (!a->b) { free(a); return NULL; }     
  a->vf = a->b;  
  a->sv = a->b + d * a->maxe; 
  return (void *)a;
}

int Push(void *a, void *ae)  
{ if( PLINA(a)) return 0;
  memcpy (VF(a), ae, DIME(a)); 
  VF(a) += DIME(a);           
  return 1;
}

int Pop(void *a, void *ae)    
{ if(VIDA(a)) return 0;
  VF(a) -= DIME(a);        
  memcpy (ae, VF(a), DIME(a)); 
  return 1;
}

int Top(void *a, void *ae) 
{ if(VIDA(a)) return 0;
  memcpy (ae, VF(a)-DIME(a), DIME(a));
  return 1;
}

Anyway, what this wants to be is a generic stack implementation with vectors, from which I don't understand why in the Top, Push and Pop functions need to refer to the stack data structure as a void *.

By generic, doesn't it want to mean that the value the data structure wants to hold is generic? This meaning that if you refer to your generic data structure as the typedef instead of void * it doesn't certainly mean that it's not generic.

I am asking this because I am about to create a Generic Stack implemented with Linked Lists and I am a bit confused.

This is my generic linked list data structure:

typedef struct Element {
    struct Element *next;
    void *value;
} TElement, *TList, **AList;

And for the Stack:

typedef struct Stack {
    size_t size;
    TList top;
} TStack, *AStack;

/* Function Definitions */
TStack InitStack(size_t);
void DeleteStack(AStack);
int Push(TStack, void*);
int Pop(TStack, void*);
int Top(TStack, void*);

Does anything seem not generic in my implementation?

Was it helpful?

Solution

Generic means that it can hold ANY data type (char*, int*, etc..), or contain any data type. Void pointers void * in C allow you to cast items as such and get those items out(having to re-cast them on retrieval.

So, it allows the program to be ignorant of the data types that you have in your custom data structure.

Referring to the structure itself(as long as you are not specifying the data that is held in said structure), does not break generalities. So, you can specifically mention your TStack in your functions as long as the data that is manipulated inside of that stack is general(id est void *).

OTHER TIPS

void* is for generic purposes. Imagine it as a pointer to the memory, where of course the memory can hold anything. By void* you mean that you do not know what you point to, but you know that you point to something.

Yes a void*can correctly implement a generic stack, but that creates a problem that you have no idea about the type of data you are storing in the Stack. The concept of void* is that it is pointing to some valid block of memory, but there is absolutely no clue as to the type of the memory. So, the code that is using this generic stack has to do type conversion explicitly. void* are used only to store data, manipulation with them are disallowed.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top