Reputation: 2552
i'm writing a c program and i've noticed that whenever i declare my array length with const variable(const size_t MAX_LEN = some number) it sends me errors. on the other hand, when i'm using (#define MAX_LEN = some number) as my array length declaration it works just fine.
the exact error i get : LinSeperator.c:45:2: error: variable length array ‘arr’ is used [-Werror=vla] double theAns, arr[MAX_LEN]; ^
could anyone help me figure out why it happens?
EDIT: here's my code: this is my LinSeperatorHelperFunc.h:
#pragma once
#include <stdio.h>
const size_t MAX_LEN = 199;
typedef struct Orange
{
double arr[MAX_LEN];
int tag;
}orange;
void learnProg(orange *o, double w[], int d);
void filePrinter(const char *output, FILE **fileIn, int d, double w[]);
this is my .c file:
#include "LinSeperator.h"
#include "LinSeperatorHelperFunctions.h"
#define NEG_ONE (-1)
#define NegToPos (2)
void LinSeperator(const char *In, const char *Out){
FILE * input;
orange o;
int d , pos, neg ,i , j;
//initializing the hypothesis vector as requested in step 1
double w[MAX_LEN];
for(i = 0 ; i<MAX_LEN ; i++){
w[i] = 0;
}
input = fopen(In,"r");
if(input == NULL){
printf("file doesnt exists");
return;
}
fscanf(input, "%d %d %d", &d , &pos, &neg);
for(i = 0; i<pos+neg ; i++){
o.tag = i<pos ? 1: -1;
for(j = 0 ; j<d ; j++){
fscanf(input, "%lf", &o.arr[j]);
//removing ',' from being scanned
if(j!= d-1){
fgetc(input);
}
}
learnProg(&o,w,d);
}
filePrinter(Out, &input, d, w);
fclose(input);
}
void filePrinter(const char* out, FILE **in, int d, double w[]){
int i;
double theAns, arr[MAX_LEN];
FILE *output = fopen(out, "w");
if (output == NULL){
printf("couldnt write to the current file");
return;
}
while(!feof(*in)){
for (i=0; i<d; i++) {
fscanf((*in), "%lf", &arr[i]);
if(feof(*in))//if we finished the checked vectors we should finish the file and the function
{
fclose(output);
return;
}
//preventing from reading the "," between each col
if(i!=d-1){
fgetc(*in);
}
}
theAns=0;
for (i=0; i<d; i++){
theAns+=arr[i]*w[i];
}
//if ans >=0 print 1 to file else -1
fprintf(output, "%d\n", NEG_ONE+NegToPos*(theAns>=0));
}
fclose(output);
}
//the learning progress algo
void learnProg(orange *o, double w[], int d){
int i, negOrPos = (*o).tag;
double theAns = 0;
for(i = 0; i<d ; i++){
theAns += ((*o).arr[i] * w[i]); //2.1
}
//has the same sign
if( (negOrPos * theAns) > 0 ){ //2.2
return ;
}
else{
for(i = 0; i<d ; i++){
w[i] += (negOrPos * (*o).arr[i]);
}
}
}
Upvotes: 1
Views: 2844
Reputation: 11453
In C, const
do not create a compile-time constant. It merely creates a read only variable. The distinction is important.
When you use:
#define MAX_LEN 701
It's a directive given to the preprocessor to replace all
occurrences of MAX_LEN
with 701
. When the compiler gets
your code, all it gets to see is the numerical constant.
C 90 standard allows to declare arrays with with numerical constant length only. However, if you were to use C 99 you could use variable length arrays.
With gcc
, you can use --std=c99
or --std=c90
to set what standard
to compile your code against.
Upvotes: 5
Reputation: 11930
It's simply a limitation of the language. You cannot use a const size_t in a array declaration. In example:
const size_t dimensions = 3;
size_t reality[dimensions]={3,8,12};
It won't compile, but
#define dimensions 3
size_t reality[dimensions]={3,8,12};
Works.
The sizes of statically-bounded arrays need to be constant expressions, and unfortunately in C that's only something like a literal constant or a sizeof expression or such like, but not a const-typed variable. You can try using dynamic allocation of array of pointers, but its more complicated to use.
As Lundin say, technically the standard C99 say that you cannot provide an initializer list to a VLA. Reference here.
Upvotes: 0
Reputation: 213513
It depends on where the array is declared.
If it is declared at file scope (outside any function) then the array size must be a constant expression, like a #define
raw number. Unfortunately C does not regard const
variables as constant expressions.
If the array is declared at local scope, the problem is just that you are using a far too old compiler, or alternatively that you have misconfigured GCC. In case of GCC, tell it to compile your code according to the C standard language: gcc -std=c11 -pedantic-errors -Wall -Wextra
.
Upvotes: 1