#include <stdio.h>
#include <stdlib.h>
typedef struct queue
{
int *arr, // array to store values
size, // queue size (array size)
put, // index location which the next value will be pushed in
take, // index location which the next value will be popped out
countVals; // Counts the number of values that the queue contains
} queue;
// queue nitialization
void newQueue (queue *q, int size)
{
if (size < 0)
q->arr = NULL;
else
{
q->arr = (int*) malloc (sizeof (int) * size);
q->size = size;
q->put = q->take = q->countVals = 0;
}
}
// free array allocated to queue
void freeQueue (queue *q)
{
free (q->arr);
}
// is the queue full?
int isFullQueue (queue q)
{
return q.countVals == q.size;
}
// is the queue empty?
int isEmptyQueue (queue q)
{
return q.countVals == 0;
}
// how many values queue contains?
int countQueueVals (queue q)
{
return q.countVals;
}
// push value to queue
void pushQueue (queue *q, int val)
{
if (q->arr && !isFullQueue (*q))
{
q->arr[q->put] = val;
q->put = (q->put + 1) % q->size;
q->countVals++;
}
}
// pop out value from queue
void popQueue (queue *q)
{
if (q->arr && !isEmptyQueue (*q))
{
q->take = (q->take + 1) % q->size;
q->countVals--;
}
}
// What is the value at top of queue
int topQueue (queue q)
{
if (q.arr && !isEmptyQueue (q))
return q.arr[q.take];
return -1;
}
// show all queue values
void showQueue (queue q)
{
if (q.arr)
while (!isEmptyQueue(q))
{
printf ("%d ", topQueue(q));
popQueue (&q);
}
// printf ("\n");
}
// are values of queue arranged in palindrome?
int isQueuePalindrome (queue q)
{
int i, num1, num2;
queue tmpQ;
if (!q.arr)
return -1;
newQueue (&tmpQ, q.countVals);
while (!isEmptyQueue(q))
{
pushQueue (&tmpQ, topQueue(q));
popQueue (&q);
}
while (tmpQ.countVals > 1)
{
for (i = 0; i < tmpQ.countVals - 1; i++)
{
num1 = topQueue (tmpQ);
popQueue (&tmpQ);
pushQueue (&tmpQ, num1);
}
num1 = topQueue (tmpQ);
popQueue (&tmpQ);
num2 = topQueue (tmpQ);
popQueue (&tmpQ);
if (num1 != num2)
{
freeQueue (&tmpQ);
return 0;
}
}
freeQueue (&tmpQ);
return 1;
}
void main ()
{
queue q;
newQueue (&q, -1);
showQueue (q);
printf ("%d\n", isQueuePalindrome(q)); // -1
newQueue (&q, 5);
showQueue (q);
printf ("-> %d\n", isQueuePalindrome (q)); // 1
pushQueue (&q, 10);
showQueue (q);
printf ("-> %d\n", isQueuePalindrome (q)); // 1
pushQueue (&q, 10);
showQueue (q);
printf ("-> %d\n", isQueuePalindrome (q)); // 1
popQueue (&q);
pushQueue (&q, 20);
showQueue (q);
printf ("-> %d\n", isQueuePalindrome (q)); // 0
pushQueue (&q, 30);
showQueue (q);
printf ("-> %d\n", isQueuePalindrome (q)); // 0
pushQueue (&q, 20);
showQueue (q);
printf ("-> %d\n", isQueuePalindrome (q)); // 0
pushQueue (&q, 10);
showQueue (q);
printf ("-> %d\n", isQueuePalindrome (q)); // 1
}
I try to check with function, whether are values of queue arranged in palindrome.
I can't figure out why when I call the function, the function changes it values, even though I do't send the queue as a pointer. Also, I can't figure out why it's happens only when the queue is full.
The function checks the queue according to the following algorithm:
update:
Thanks to Christian Gibbons and Yunnosch, I fixed the problem with another queue (I could only copy the array, but I wanted the entire solution to be by queue).
I wonder if there is a way to check whether a queue is a palindrome without any additional data structure (queue, stack, array, etc.)?
If you copy a struct which contains a pointer, then the copy will contain the same pointer address, both point to the same memory.
If you then change that memory, the pointers in both copies, though unchanged themselves, will point to the same memory, because they have not been changed, not in spite of that.
So the copy and the original, both still contain the pointer pointing to the changed values.