-4

I have to write code which will be checking if input in my code is correct. I have to prevent entering letters, NULLs etc.

I tried simple if(*tab == NULL).. but I can't compare float and void values.

int avg(const float* tab, unsigned int size, float *result)
{
    if( size <= 0)
    {
        return 1;
    }
    float suma = 0;
    for(unsigned int i=0;i<size;i++)
    {
        suma=suma + *(tab+i);
    }
    *result = suma / size;
    return 0;
}
ice592
  • 27
  • 2
  • 7
  • 3
    C is not like JavaScript or SQL: value types cannot be `NULL` because they aren't pointers. `NULL` is just a constant value equal to zero (in most compilers). Pointers are just (special) integer numbers. – Dai Mar 24 '19 at 16:47
  • This question is literally like asking how to compare apples to oranges. – klutt Mar 24 '19 at 16:50
  • 1
    If you want to make sure that the caller is not passing a null pointer, just compare the pointer to `NULL` as in `tab == NULL` (or `tab != NULL`). If you use `*tab` then you dereference the pointer which will not work well if it's a null pointer. – Some programmer dude Mar 24 '19 at 16:52
  • 1
    Regarding pointers and dereferencing, note that the expression `*(tab+i)` is *exactly* equal to `tab[i]`. The latter is usually easier to read and understand (and less to write). – Some programmer dude Mar 24 '19 at 16:53
  • So what can I do if checking machine types "int res = avg(NULL, 13, &result);" ??? I know this question is stupid, but I have no idea have to prevent entering NULL. – ice592 Mar 24 '19 at 16:54
  • @Someprogrammerdude I cannot use table reference by [] – ice592 Mar 24 '19 at 16:55
  • You can't prevent a caller of your function from passing any weird arguments to your function. What you can do is do some validation (like `if (tab == NULL) return 1;` or the size check you already do. If the user is passing a non-null pointer, then it's the fault of the caller and not you if it's not a valid pointer. – Some programmer dude Mar 24 '19 at 16:56
  • Note that `if (*tab != NULL)` is the same as `if (*(tab + 0) != NULL)`. In other words, just as `*(tab+i)` is the entry in the table at index `i`, `*tab` is the entry in the table at index 0. The entry at index 0 is a `float`, and `NULL` is typically the value 0 cast to a `void *`. Hence the compiler warning that you're comparing a `float` to a `void *`. – user3386109 Mar 24 '19 at 17:04
  • 2
    BTW, when asking a question about a compiler warning, be sure to follow these three simple steps. 1) Post the exact code that generates the warning. 2) Post the exact text of the warning. 3) Add a comment to the code that indicates the line where the warning occurred. – user3386109 Mar 24 '19 at 17:08
  • I think this question should be upvoted. Sure, it's a very beginnerish mistake, but I can imagine more people wondering about this. – klutt Mar 24 '19 at 17:24

1 Answers1

2

C does not store values the same way as Javascript or Python. In C, there's no such thing as a variable without value. You can never determine if a variable is initialized or not only by looking at the variable itself. A variable can be uninitialized, but using the variable then would lead to undefined behavior and the most likely consequence of ub in this case is that you get a random value that has a high probability of being zero.

If you do the declaration float f, then you reserve a certain amount of memory (usually 4 bytes for a float). Each time you use f in an expression, then whatever bit pattern that is found at the address &f will be interpreted as a float. Some bit patterns may be special for floats but NULL is not one of them, but when it comes to integers, then EVERY bit pattern is a valid regular integer.

You simply have to make sure that tab is properly initialized before passing it to your function. The function itself cannot determine if that's the case.

In C, NULL is a constant, usually of type void*, but it may also be of type int. The intended purpose is for pointers and should not be used for anything else.

Furthermore, C is a statically typed language, which means that a variable can never change type. A float can never contain letters. You can, via casting, make a float to contain the same bit pattern as an integer, a four character string, a pointer or something else, but most likely the result would not make sense.

klutt
  • 30,332
  • 17
  • 55
  • 95
  • 2
    I would contest the "strongly typed" since you can reinterpret/cast any data in C to whatever type you like and neither the compiler nor the executing machine will stop you (well, until something breaks). Unlike in most higher-level languages like Python, Java, Smalltalk etc. where you cannot pretend that one object is of a different type than it actually is. I would therefore write "statically typed" instead. The distinction is hardly relevant for the question though. – JayK Mar 24 '19 at 17:39