Newbe question about Void Loop and Void Setup functions

I have been working with a simple sketch involving using a TPM36 sensor.

There are a few items of the code I'm not understanding. Can anyone explain what the functions
of these two statements?

void setup (void)

and

void loop (void)

What is the purpose of the (void) statement?


Setup() is the function that only runs once upon controller reset. You put your setup code there (like serial.begin() or
wire.begin()). Loop() is where the code that runms ovewr and over goes (your program). Loop() and setup() are functions. A function with void in front is a void function and so will not return a value. The void after means that the function will accept no arguments.

Thank you.

Can you expand or example what you mean by "The void after means that the function will accept no arguments"?

Here is the sketch I am working with. Didn't attach correctly on first post.

Trying to learn each part of the code. Have not seen void used like this in any of the example I have studied before.

#define aref_voltage 3.3         // we tie 3.3V to ARef and measure it with a multimeter!
   
//TMP36 Pin Variables
int tempPin = 1;        //the analog pin the TMP36's Vout (sense) pin is connected to
                        //the resolution is 10 mV / degree centigrade with a
                        //500 mV offset to allow for negative temperatures
int tempReading;        // the analog reading from the sensor
 
void setup(void) {
  // We'll send debugging information via the Serial monitor
  Serial.begin(9600);   
 
  // If you want to set the aref to something other than 5v
  analogReference(EXTERNAL);
}
  
void loop(void) {
 
  tempReading = analogRead(tempPin);  
 
  Serial.print("Temp reading = ");
  Serial.print(tempReading);     // the raw analog reading
 
  // converting that reading to voltage, which is based off the reference voltage
  float voltage = tempReading * aref_voltage;
  voltage /= 1024.0; 
 
  // print out the voltage
  Serial.print(" - ");
  Serial.print(voltage); Serial.println(" volts");
 
  // now print out the temperature
  float temperatureC = (voltage - 0.5) * 100 ;  //converting from 10 mv per degree wit 500 mV offset
                                               //to degrees ((volatge - 500mV) times 100)
  Serial.print(temperatureC); Serial.println(" degrees C");
 
  // now convert to Fahrenheight
  float temperatureF = (temperatureC * 9.0 / 5.0) + 32.0;
  Serial.print(temperatureF); Serial.println(" degrees F");
 
  delay(1000);
}

I think I see what you mean. The void after setup() and loop() are not really necessary. I am not a C programmer so my educated guess is that the author puts void there for clarity. Setup() is the same as setup(void) and for loop the same. If a function accepts arguments they must be included instead of void or empty (). Like void myFunction(int data)..

it is one of the differences between C and C++ :

in C++ (and arduino uses C++ compiler), foo(); and foo(void); means the same : the function takes no argument.

In C, they are not the same :

a function prototype such as foo(); means that the arguments are undefined, and the function may be defined with one or more argument (at least, it was true in K&R C, I'm not sure it is still the case). Thus in C, if you want to declare a function which takes no argument, you must use 'void' : foo (void) ;

I think that most programmers that have learned C before C++ tend to use foo(void); in C++, even if it is not mandatory :wink:

a function prototype such as foo(); means that the arguments are undefined

Hmm. I think you'll get errors in most modern C implementations.
Technically, "void foo();" will be a valid prototype for an "old-style" C function

void foo(a,b, c)
    int a; char b; double c;
{
    printf("%3.3f\n", a*b*c);
}

But DON'T DO THOSE!!! gcc gives an error if you have the above prototype with a modern function:

void foo( int a, char b, double c)
{
    printf("%3.3f\n", a*b*c);
}

westfw:

a function prototype such as foo(); means that the arguments are undefined

Hmm. I think you'll get errors in most modern C implementations.
Technically, "void foo();" will be a valid prototype for an "old-style" C function

void foo(a,b, c)

int a; char b; double c;
{
   printf("%3.3f\n", abc);
}



But DON'T DO THOSE!!! gcc gives an error if you have the above prototype with a modern function:

void foo( int a, char b, double c)
{
   printf("%3.3f\n", abc);
}

K&C C before the ANSI X3J11 committee did not have prototypes at all. It only had the old style declarations. However, in the old style declarations, you had the implicit conversions happening. So any char or short argument are converted implicitly to int, and float arguments are converted to double. Here is the wording from the C99 standard:

If the expression that denotes the called function has a type that does not include a
prototype, the integer promotions are performed on each argument, and arguments that
have type float are promoted to double. These are called the default argument
promotions. If the number of arguments does not agree with the number of parameters,
the behavior is undefined.

C++ being a language to improve upon C required the user to always prototype his/her function.

During the initial process which lead up to the 1989 ANSI C standard which was replaced by the 1990 ISO C standard (*), we (**) took prototypes from the C++ language (as well as the way of declaring const/volatile, though const is slightly different between C/C++). However:

void foo ();

already had a meaning in C, of declaring foo as a function returning nothing, but nothing was said about the arguments, while in C++, it meant you were saying that foo did not take any arguments.. So we added the use of void to explicitly say that foo has no arguments. Later when C++ got standardized, it imported the use of void from C back into its languages.

During the standardization process, we tended to call the rule where the compiler creates a prototype for you the Miranda rule, modifying the US Miranda rule (you have the right to an lawyer, if you can not afford one, one will be appointed by the court) to be you have the right to a prototype, if you cannot afford a prototype, one will be appointed to by the compiler (hey what can I say, things get a little punchy when you are with the same people for 4-5 days a time).

While I know that I can avoid the void in the Arduino context, since you are always dealing with C++, I tend to always use void just because I am a C guy.

(*) ANSI is an American (US) standards body. After the ANSI C standard came out, it was promoted to be an ISO standard which is the world wide standards body. So while people talk about ANSI C, it is more correct now to say ISO C.

(**) I was on the original X3J11 standard committee, and was one of 3 members that was at the original meeting in 1983 to begin the standards process and who was still on the committee by the time the 1989 and 1990 standards came out. Originally I represented the Data General corporation (where I had written most of the DG C front end for the MV/Eclipse computers), and later the Open Software Foundation. When I moved on to Cygnus Solutions, I dropped out of the standards process, but I had been in it for 10 1/2 years.

Ah. I see what I did; by having a "char b" argument in my function definition, the function could no longer possibly match the default promotion rules, and I got an error. If I have

void foo();

void foo( int a, double b)
{
    printf("%3.3f\n", a*b);
}

It will compile just file. (Ouch. I didn't know that!)

Originally I represented the Data General corporation ...

Och, we used to use DG. That brings back memories. :slight_smile:

This may also help seeking an answer to the original question.
Whats the meaning of VOID? And from my understanding the bootloader (operating system of sorts) cannot have a program that ends, so a loop must exist. The program you send the microprocessor can have other functions but once those functions are completed it must end with a loop

void loop()
{
// ...
}
.
Between setup and loop you could have other functions.
That my understanding.

That my understanding.

It's completely wrong. The bootloader does not have anything to do with running the sketch after it is loaded. The sketch does NOT have to have a loop() function. One can define a main() function, to stop the IDE adding a main() function. The user-defined main() does not have to call setup() or loop() so neither of those functions would then be needed.