Function of curly bracket without keyword unclear [duplicate] - c

This question already has answers here:
Unnecessary curly braces in C++
(14 answers)
Closed 9 years ago.
I found in a programm that code fragment
{
Aux_U16 = 16;
}
so the question is : why there a this curly brackets. No keyword like if or switch are visible.
So what function have curly brakets in the programming language C, if they are written without any keyword

It's sometimes nice since it gives you a new scope, where you can more "cleanly" declare new (automatic) variables.
Those braces are controlling the variable scope.And since variables with automatic storage are destroyed when they go out of scope.
It is simply to isolate a block of code that achieves a particular (sub)purpose. It is rare that a single statement achieves a computational effect I want; usually it takes several.

Normally they'd be used to constrain scope of a variable, but in with your example Aux_U16 = 16; no new variable is defined, so there must be a pre-existing variable named Aux_16, and beyond the end of the block it will continue to have whatever value it was last set to within the block.
Limiting the scope allows you to create, for example, a new variable named i, without needing to think about the state of any i outside of that block -- unfortunately, as in the example you gave, the compiler wouldn't notice the difference between definition and assignment, and you could end up corrupting a variable you thought you had protected.
The other common reason to find things that way is simply cut-and-paste. There's nothing wrong with free-standing blocks like this, and sometimes people just forget to delete the leftovers. Or they might have had temporary variables in there until they edited the code and they went away. Or they might mean it as a note to themselves that the code inside the block belongs together.

{} brackets define the scope. These brackets must have been inside any function or method.
If you are inside a function you can have {} blocks.
NOTE:- If you just add them and compile without any scope it will give you compile time error.

Related

What's the difference between global or local variables regarding the main function? [closed]

Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 3 years ago.
Improve this question
While I know what's the difference between local and global variables I just can't understand if it's important at all, especially when talking about local variables inside the main function.
For example what's the difference here except that we can't use the testvar in the second case in other functions?
First Case:
#include <stdio.h>
int testvar;
Second Case:
#include <stdio.h>
int main(void){
int testvar;
}
Edit: What I mean is that if I am going only to use a variable inside main then does declaring it as global have any advantage Or that in this specefic case nothing different at all?
Good practice in software engineerIng is to limit the scope of names to where they are used. If testvar is declared outside of main, then it is visible to code outside main. This exposes it to bugs in which some other code uses testvar when it was intended to use some other object (either another object with a different name that was mistyped or an object with the same name, but a different instance of it was desired). Additionally, because it is declared with int testvar; and not static int testvar;, it will be linked with other objects named testvar in other modules. This is a serious problem—it happens that one author of some routines used some name like AmountOfMemory for their own purposes and another author of other routines used the same name for their own purposes, and both pieces of code work separately, but, when linked into the same program, they break. For this reason, good code avoids global variables.
If testvar is declared inside main, none of those errors can occur. The probability of writing a good program is increased. Thus, if testvar is not needed (by name) outside of main, declaring it inside main is preferable.
There is also an issue of lifetime. Similarly to scope (where a name is visible), we prefer to limit lifetime (when an object exists). In the case of an object defined inside main, its lifetime is effectively the same as an object declared outside of any function—it will exist for the duration of program execution. So lifetime is not a great concern here. However, there is a situation in which it is. In C, it is permissible to call main inside the function. This is rarely used. However, if it is used and if testvar is defined outside main, there will be only one instance of it, and all executions of main will share them. If testvar is defined inside main, each execution of main will have its own instance of testvar, separate from the others.
Another difference between objects defined inside functions and those defined outside functions is that C automatically initializes objects defined outside functions to zero by default. This however would not affect the choice of where to define the object as an explicit initialization can be provided as desired.
"While I know what's the difference between local and global variables I just can't understand if it's important at all"
For me, when learning C, I felt like I didn't really understand the difference between local and global variables, until I understood why it's important.
Eric Postpischil's answer about scope and lifetime says it all. It's not a mere difference in how and where you can use the variables; it's the broader implications about what can happen because of that access.
So don't think in terms of "if I am going only to use a variable inside main()"; think in terms of encapsulation, modularity, interfaces, and shared code. I would go so far as to suggest never using global variables; any time you are tempted to do so, it will be worth the effort to find another way to accomplish what you are trying to do. Your future self will thank you for solid programming habits you foster now.
For example what's the difference here except that we can't use the testvar in the second case in other functions?
From a C standard point of view that is actually the main difference (see later for another differance). If you define the variable inside main it has automatic storage duration and is only accessible using its variable name inside main. If you define the variable outside main it has static storage duration and can be accessed using its variable name from anywhere in the code.
One difference is that variables with static storage duration are default initialized while variables with automatic storage duration are left uninitialized. So in your first example testvar will be initialized to zero while it is uninitialized in the second example.

Why redeclaration of variable is allowed inside loop and if condition which are declared out side of loop or if condition already? [duplicate]

This question already has answers here:
Why doesn't declaring a variable with the same name outside and inside a loop produce an error?
(4 answers)
Closed 7 years ago.
#include <stdio.h>
int main()
{
int a=9;
if(a<10){
int a = 20;
++a;
printf("%d\n",a);
}
printf("%d\n",a);
}
Why redeclaration of a is allowed in loop and if condition here?
Why can't we increment or decrement variable inside loop or if statement which are delclared outside of loop or if statement??
It isn't a "redeclaration", it is a declaration of a brand new variable with the same name. All access to a within the if statement will refer to the new local variable a with value 20 and not to the previously allocated one with value 9.
The reason why it is allowed is because it allows you to give names to local variables without worrying about what names that are already taken elsewhere.
Mainly that is a concern between local scope and global scope, but the same rules apply recursively to local scopes inside the local scope.
If it wasn't allowed, it would be very hard to maintain large projects, as you would constantly run into naming collisions.
Generally though, it is considered very poor practice to give the same name to different variables in different scopes, you should avoid doing that whenever possible.
A variable inside a nested block can have the same name as a variable of the outer block. This is called name hiding.
The variable define in the nested block "hides" the variable of the outer block.
At the end of the nested block, the variable local to this block is destroyed. So the printf statement is executed with the variable defined at the beginning of the main function.
I think you are expecting for changing i.e reassigning value of a, not a redeclaration. So, inside loop just do as a=20 instead int a=20.
Redeclaration is not possible for same variable. Once declared any variable the memory is allocated for it. If you redeclare it will create conflicts or error.

Difference of variable declaration in for statement in C [duplicate]

This question already has answers here:
Declaring variables inside loops, good practice or bad practice?
(9 answers)
Closed 7 years ago.
let's assume that it is not only in visual studio but also in C99, C11 and etc.
there are two different ways of declaring variable "i" in for statement.
1)
int i;
for(i = 0 ; i < index ; ++i)
2)
for(int i = 0 ; i < index ; ++i)
Both work same. but I think there will be some difference between them.
Do you have any idea about that?
If yes, please let me know.
I just wondering about your opinion, and how it works differently.
Sorry. for answers, I know that the scope of "i" is different.
Is there any difference in view of system(I mean memory or etc.) or compiler work differently or assembled code is different or something like this.
The only difference is that in the first case, the variable i is outside for scope so you could use it later on. There are no differences in term of efficiency.
If you use i only once, then definitely the 2nd case is better:
for(int i = 0 ; i < index ; ++i)
If you have loops that use index i, then it might make sense declaring it outside all loops.
But generally, the rule is to limit the scope of the variable - so the 2nd case is better. It's usually safer to limit the scope of the variable.
It'd worth noting that the 2nd case syntax only works with C99 or newer C11 (did not work with old C89). So some compilers would complain if you declare variable inside the loop. For example, gcc requires explicit flag -std=c99 to allow that syntax.
The scope and lifetime of i is different.
In the second example it is just inside the loop body. In the first, it extends beyond.
Apart from that, they are equal.
Declaring a new variable in the initialization of the for loop is a C99 extension.
C89 requires that variables be declared at the beginning of a block.
Semantically, declaring variables in the initialization portion of the loop would limit the variables' scope to the body of the loop.
Limiting the scope is often desired to avoid misuse of variables after the body of the for loop has executed. For example, if you are doing a simple iteration, you may not want your index to exist after the for loop.
There is no right answer on which to use. The question becomes what you want your scope to be, and what compilers/language versions you intended to support.
In C99 the correct way is No 1). It requires the variables are declared before use. Looks like your compiler supports several standards, therefore it looks transparent to you what construction to use, and they all result in the same behavior. My personal preference in this case is 2) because it reduces scope of the variable i, and also prevents from unitialized value use (less risky).

Temporary variables in C

I am using XC32 compiler by Microchip, and it does not allow declaration of variables inside loops (does not support C99), so I can not do this:
for(int i = 0;i<10;i++)
{do w/e}
I would hate to make it a global, because it would be hard to keep track of it's value in big projects, using the same thing in various loops, even if you initialize it to i = 0 in every loop. I even had a bug with this, when it turned out to do weird stuff if you have a few nested loops using the same i.
As far as I understand, I can't "undeclare" it manually, but variables defined inside a block of code are undeclared after the pass trough the block? Is this true, and does that mean that this this code will act like the code above:
{
int i;
for(i = 0;i<10;i++)
{do w/e}
}//no i anymore?
According to C99 standard, the scope of a variable declared in the clause statement of the for loop is restricted in scope to that loop.
In C89 / C90, that clause is merely an optional expression.
Therefore in C89 / C90 you can confidently emulate the C99 behaviour with
{ /*open scope block*/
/* your declaration here, including possible definition*/
for (expression; ...){
}
} /*close scope block*/
By putting it in a block you will indeed be rid of it at the conclusion of the block in question.
What this means exactly, however, depends on the compiler, the architecture, and the environment.
The variable scope is inside the block in which it is defined. So once the block is finished you cannot access the variable.
You may find this helpful:- Local variables display as “Out of Scope” when they are most clearly NOT out of scope.

Refactoring global to local. Should they be static or not?

I'm refactoring "spaghetti code" C module to work in multitasking (RTOS) environment.
Now, there are very long functions and many unnecessary global variables.
When I try to replace global variables that exists only in one function with locals, I get into dilemma. Every global variable is behave like local "static" - e.g. keep its value even you exit and re-enter to the function.
For multitasking "static" local vars are worst from global. They make the functions non reentered.
There are a way to examine if the function is relay on preserving variable value re-entrancing without tracing all the logical flow?
Short answer: no, there isn't any way to tell automatically whether the function will behave differently according to whether the declaration of a local variable is static or not. You just have to examine the logic of each function that uses globals in the original code.
However, if replacing a global variable with a static local-scope variable means the function is not re-entrant, then it wasn't re-entrant when it was a global, either. So I don't think that changing a global to a static local-scope variable will make your functions any less re-entrant than they were to start with.
Provided that the global really was used only in that scope (which the compiler/linker should confirm when you remove the global), the behaviour should be close to the same. There may or may not be issues over when things are initialized, I can't remember what the standard says: if static initialization occurs in C the same time it does in C++, when execution first reaches the declaration, then you might have changed a concurrency-safe function into a non-concurrency-safe one.
Working out whether a function is safe for re-entrancy also requires looking at the logic. Unless the standard says otherwise (I haven't checked), a function isn't automatically non-re-entrant just because it declares a static variable. But if it uses either a global or a static in any significant way, you can assume that it's non-re-entrant. If there isn't synchronization then assume it's also non-concurrency-safe.
Finally, good luck. Sounds like this code is a long way from where you want it to be...
If your compiler will warn you if a variable is used before initialized, make a suspected variable local without assigning it a value in its declaration.
Any variable that gives a warning cannot be made local without changing other code.
Changing global variables to static local variables will help a little, since the scope for modification has been reduced. However the concurrency issue still remains a problem and you have to work around it with locks around access to those static variables.
But what you want to be doing is pushing the definition of the variable into the highest scope it is used as a local, then pass it as an argument to anything that needs it. This obviously requires alot of work potentially (since it has a cascading effect). You can group similarly needed variables into "context" objects and then pass those around.
See the design pattern Encapsulate Context
If your global vars are truly used only in one function, you're losing nothing by making them into static locals since the fact that they were global anyway made the function that used them non-re-entrant. You gain a little by limiting the scope of the variable.
You should make that change to all globals that are used in only one function, then examine each static local variable to see if it can be made non-static (automatic).
The rule is: if the variable is used in the function before being set, then leave it static.
An example of a variable that can be made automatic local (you would put "int nplus4;" inside the function (you don't need to set it to zero since it's set before use and this should issue a warning if you actually use it before setting it, a useful check):
int nplus4 = 0; // used only in add5
int add5 (int n) {
nplus4 = n + 4; // set
return nplus4 + 1; // use
}
The nplus4 var is set before being used. The following is an example that should be left static by putting "static int nextn = 0;" inside the function:
int nextn = 0; // used only in getn
int getn (void) {
int n = nextn++; // use, then use, then set
return n;
}
Note that it can get tricky, "nextn++" is not setting, it's using and setting since it's equivalent to "nextn = nextn + 1".
One other thing to watch out for: in an RTOS environment, stack space may be more limited than global memory so be careful moving big globals such as "char buffer[10000]" into the functions.
Please give examples of what you call 'global' and 'local' variables
int global_c; // can be used by any other file with 'extern int global_c;'
static int static_c; // cannot be seen or used outside of this file.
int foo(...)
{
int local_c; // cannot be seen or used outside of this function.
}
If you provide some code samples of what you have and what you changed we could better answer the question.
If I understand your question correctly, your concern is that global variables retain their value from one function call to the next. Obviously when you move to using a normal local variable that won't be the case. If you want to know whether or not it is safe to change them I don't think you have any option other than reading and understanding the code. Simply doing a full text search for the the name of the variable in question might be instructive.
If you want a quick and dirty solution that isn't completely safe, you can just change it and see what breaks. I recommend making sure you have a version you can roll back to in source control and setting up some unit tests in advance.

Resources