1
/*implementation of strrev i.e. string reverse function*/

#include<stdio.h>
#include<string.h>

/*length of the string i.e. cells in the string*/
static const unsigned int MAX_LENGTH = 100;
//static const int MAX_LENGTH = -100;

/*reverses the string*/
void reverseString(char[]);
/*swaps the elements in the cells of a string*/
void swap(char[], int, int);

/*runs the program*/
int main()
{
    char string[MAX_LENGTH];
    //char string[0];  //no error!
    //char string[-1]; //error! 

    gets(string);
    reverseString(string);
    printf("\n%s", string);

    return 0;
}

void reverseString(char string[])
{
    int i;
    for(i = 0; i < (strlen(string) / 2); i++)
    {
        swap(string, i, (strlen(string) - 1 - i));
    }
}

void swap(char string[], int i, int j)
{
    int temp = string[i];
    string[i] = string[j];
    string[j] = temp;
}

Look at the main function. If you replace the first line "char string[MAX_LENGTH];" with "char string[-1];", the compiler shows error. (because string of negative length makes no sense). However, if you replace the 7th line of this code (where I declared const MAX_LENGTH) with the code written in comments in line 8 (in which MAX_LENGTH is assigned a -ve value), there is no compilation error. Why?

Also, why there is no error in declaring zero length string. How does zero length string makes sense to compiler but not a negative length string?

1 Answers1

4

Because it's not the same thing.

  • In the first case, you're defining an array, using a fixed, compile-time size
  • In the second case, you're defining a variable length array or VLA.

The compiler does the allocation at run time in the second case (with this -100 value it isn't going to end well), because the const isn't really a constant in C, it just tells the compiler you aren't to change the value (and also allows some optimizations). So the result is undefined behaviour (more here: Declaring an array of negative length)

If you want the same behaviour use a #define

 #define MAX_LENGTH -100    // will raise a compilation error

or as suggested in comments, an enumerated constant:

enum { MAX_LENGTH = -100 };    // will raise a compilation error

If you want to protect your declarations, use assert

assert(MAX_LENGTH > 0);
char string[MAX_LENGTH];

As for the zero-length element, no need to repeat what's already been answered: What's the need of array with zero elements? (in a nutshell, it's useful at the end of a structure to be able to have varying length)

Jean-François Fabre
  • 137,073
  • 23
  • 153
  • 219
  • You may also consider explaining two's complement, and why assigning `-1` to an `unigned` may don't get you what you want. – Inrin Aug 21 '18 at 10:22
  • 1
    true but OP seems to be aware: in the commented question code: `static const int MAX_LENGTH = -100`: unsigned is gone. Else, true that the value would be `INT_MAX-100+1` probably too big for auto memory! – Jean-François Fabre Aug 21 '18 at 10:39
  • An alternative to using a `#define` is to use an enumerated constant. – Ian Abbott Aug 21 '18 at 10:47