Parameter Passing By Value Result & Name - parameter-passing

I am trying to understand how the concepts of parameter passing by Value Result and parameter passing by Name would apply to the following program:
// GLOBAL variables
int num[10] = {0,0,0,0,0,0,0,0,0,0}; // Subscripts start at 0 as in C++
int index = 1;
void somefun(int alpha, int beta)
{
alpha = 7;
num[index] = 33;
index = index - 6;
num[alpha] = 44;
beta = 55;
}
void main()
{
somefun( index, num[index + 4] ); // Function Call
}
This program is pseudo-code, not specific to any language, and the array subscripts start at 0.
If someone could help me understand how this program would work with parameter passing by Value Result and parameter passing by Name, I would greatly appreciate it. Thank you.
Unfortunately, I was not able to try anything on my own thus far.

Related

How can this be the output?

It is simple program, but the output of the program is so unexpected .
Programming language : ActionScript 3.0
So, we have 3 kinds of syntax:
// 1. Variable declaration.
var a:int;
// 2. Assign value to variable.
a = 0;
// 3. Declare variable and assign value in one go.
var b:int = 1;
The tricky moment is that in AS3 variable declaration is NOT an operation. It is a construction that tells compiler you are going to use a variable with a certain name and type within a given context (as a class member or as a timeline variable or as a local variable inside a method). It literally does not matter where in the code you declare your variables. AS3 is, I must admit, ugly from this very perspective. The following code might look weird yet it is syntactically correct. Lets read and understand what it does and why.
// As long as they are declared anywhere,
// you can access these wherever you want.
i = 0;
a = 0;
b = -1;
// The 'for' loop allows a single variable declaration
// within its parentheses. It is not mandatory that
// declared variable is an actual loop iterator.
for (var a:int; i <= 10; i++)
{
// Will trace lines of 0 0 -1 then 1 1 0 then 2 2 1 and so on.
trace(a, i, b);
// You can declare a variable inside the loop, why not?
// The only thing that actually matters is that you assign
// the 'a' value to it before you increment the 'a' variable,
// so the 'b' variable will always be one step behind the 'a'.
var b:int = a;
a++;
}
// Variable declaration. You can actually put
// those even after the 'return' statement.
var i:int;
Let me say it again. The place where you declare your variables does not matter, just the fact you do at all. Declaring variable is not an operation. However, assigning a value is. Your code actually goes as following:
function bringMe(e:Event):void
{
// Lets explicitly declare variables so that assigning
// operations will come out into the open.
var i:int;
var score:int;
for (i = 1; i <= 10; i++)
{
// Without the confusing declaration it is
// obvious now what's going on here.
score = 0;
score++;
// Always outputs 1.
trace(score);
// Outputs values from 1 to 10 inclusive, as expected.
trace(i);
}
}

C - pass array as parameter and change size and content

UPDATE: I solved my problem (scroll down).
I'm writing a small C program and I want to do the following:
The program is connected to a mysql database (that works perfectly) and I want to do something with the data from the database. I get about 20-25 rows per query and I created my own struct, which should contain the information from each row of the query.
So my struct looks like this:
typedef struct {
int timestamp;
double rate;
char* market;
char* currency;
} Rate;
I want to pass an empty array to a function, the function should calculate the size for the array based on the returned number of rows of the query. E.g. there are 20 rows which are returned from a single SQL query, so the array should contain 20 objectes of my Rate struct.
I want something like this:
int main(int argc, char **argv)
{
Rate *rates = ?; // don't know how to initialize it
(void) do_something_with_rates(&rates);
// the size here should be ~20
printf("size of rates: %d", sizeof(rates)/sizeof(Rate));
}
How does the function do_something_with_rates(Rate **rates) have to look like?
EDIT: I did it as Alex said, I made my function return the size of the array as size_t and passed my array to the function as Rate **rates.
In the function you can access and change the values like (*rates)[i].timestamp = 123 for example.
In C, memory is either dynamically or statically allocated.
Something like int fifty_numbers[50] is statically allocated. The size is 50 integers no matter what, so the compiler knows how big the array is in bytes. sizeof(fifty_numbers) will give you 200 bytes here.
Dynamic allocation: int *bunch_of_numbers = malloc(sizeof(int) * varying_size). As you can see, varying_size is not constant, so the compiler can't figure out how big the array is without executing the program. sizeof(bunch_of_numbers) gives you 4 bytes on a 32 bit system, or 8 bytes on a 64 bit system. The only one that know how big the array is would be the programmer. In your case, it's whoever wrote do_something_with_rates(), but you're discarding that information by either not returning it, or taking a size parameter.
It's not clear how do_something_with_rates() was declared exactly, but something like: void do_something_with_rates(Rate **rates) won't work as the function has no idea how big rates is. I recommend something like: void do_something_with_rates(size_t array_size, Rate **rates). At any rate, going by your requirements, it's still a ways away from working. Possible solutions are below:
You need to either return the new array's size:
size_t do_something_with_rates(size_t old_array_size, Rate **rates) {
Rate **new_rates;
*new_rates = malloc(sizeof(Rate) * n); // allocate n Rate objects
// carry out your operation on new_rates
// modifying rates
free(*rates); // releasing the memory taken up by the old array
*rates = *new_rates // make it point to the new array
return n; // returning the new size so that the caller knows
}
int main() {
Rate *rates = malloc(sizeof(Rate) * 20);
size_t new_size = do_something_with_rates(20, &rates);
// now new_size holds the size of the new array, which may or may not be 20
return 0;
}
Or pass in a size parameter for the function to set:
void do_something_with_rates(size_t old_array_size, size_t *new_array_size, Rate **rates) {
Rate **new_rates;
*new_rates = malloc(sizeof(Rate) * n); // allocate n Rate objects
*new_array_size = n; // setting the new size so that the caller knows
// carry out your operation on new_rates
// modifying rates
free(*rates); // releasing the memory taken up by the old array
*rates = *new_rates // make it point to the new array
}
int main() {
Rate *rates = malloc(sizeof(Rate) * 20);
size_t new_size;
do_something_with_rates(20, &new_size, &rates);
// now new_size holds the size of the new array, which may or may not be 20
return 0;
}
Why do I need to pass the old size as a parameter?
void do_something_with_rates(Rate **rates) {
// You don't know what n is. How would you
// know how many rate objects the caller wants
// you to process for any given call to this?
for (size_t i = 0; i < n; ++i)
// carry out your operation on new_rates
}
Everything changes when you have a size parameter:
void do_something_with_rates(size_t size, Rate **rates) {
for (size_t i = 0; i < size; ++i) // Now you know when to stop
// carry out your operation on new_rates
}
This is a very fundamental flaw with your program.
I want to also want the function to change the contents of the array:
size_t do_something_with_rates(size_t old_array_size, Rate **rates) {
Rate **new_rates;
*new_rates = malloc(sizeof(Rate) * n); // allocate n Rate objects
// carry out some operation on new_rates
Rate *array = *new_rates;
for (size_t i = 0; i < n; ++i) {
array[i]->timestamp = time();
// you can see the pattern
}
return n; // returning the new size so that the caller knows
}
sizeof produces a value (or code to produce a value) of the size of a type or the type of an expression at compile time. The size of an expression can therefore not change during the execution of the program. If you want that feature, use a variable, terminal value or a different programming language. Your choice. Whatever. C's better than Java.
char foo[42];
foo has either static storage duration (which is only partially related to the static keyword) or automatic storage duration.
Objects with static storage duration exist from the start of the program to the termination. Those global variables are technically called variables declared at file scope that have static storage duration and internal linkage.
Objects with automatic storage duration exist from the beginning of their initialisation to the return of the function. These are usually on the stack, though they could just as easily be on the graph. They're variables declared at block scope that have automatic storage duration and internal linkage.
In either case, todays compilers will encode 42 into the machine code. I suppose it'd be possible to modify the machine code, though that several thousands of lines you put into that task would be much better invested into storing the size externally (see other answer/s), and this isn't really a C question. If you really want to look into this, the only examples I can think of that change their own machine code are viruses... How are you going to avoid that antivirus heuristic?
Another option is to encode size information into a struct, use a flexible array member and then you can carry both the array and the size around as one allocation. Sorry, this is as close as you'll get to what you want. e.g.
struct T_vector {
size_t size;
T value[];
};
struct T_vector *T_make(struct T_vector **v) {
size_t index = *v ? (*v)->size++ : 0, size = index + 1;
if ((index & size) == 0) {
void *temp = realloc(*v, size * sizeof *(*v)->value);
if (!temp) {
return NULL;
}
*v = temp;
// (*v)->size = size;
*v = 42; // keep reading for a free cookie
}
return (*v)->value + index;
}
#define T_size(v) ((v) == NULL ? 0 : (v)->size)
int main(void) {
struct T_vector *v = NULL; T_size(v) == 0;
{ T *x = T_make(&v); x->value[0]; T_size(v) == 1;
x->y = y->x; }
{ T *y = T_make(&v); x->value[1]; T_size(v) == 2;
y->x = x->y; }
free(v);
}
Disclaimer: I only wrote this as an example; I don't intend to test or maintain it unless the intent of the example suffers drastically. If you want something I've thoroughly tested, use my push_back.
This may seem innocent, yet even with that disclaimer and this upcoming warning I'll likely see a comment along the lines of: Each successive call to make_T may render previously returned pointers invalid... True, and I can't think of much more I could do about that. I would advise calling make_T, modifying the value pointed at by the return value and discarding that pointer, as I've done above (rather explicitly).
Some compilers might even allow you to #define sizeof(x) T_size(x)... I'm joking; don't do this. Do it, mate; it's awesome!
Technically we aren't changing the size of an array here; we're allocating ahead of time and where necessary, reallocating and copying to a larger array. It might seem appealing to abstract allocation away this way in C at times... enjoy :)

Getting a MySQL Query to save as a global Variable is C

I am having issues getting a function to run and having the results of a MySQL query to be saved as a variable that other functions can use and call upon. I know the results get read from the table as a string. I was able to do this fine when getting the results and converting it to a float and then passing the results to a pointer. But I can not seem to figure out how to get the results as a string, and compare it with another string to see if they match or do not. No matter what I have tried to do, I can not seem to get a value to be saved as a string to a variable outside the function.
Here is the code of how I got it to work as a float:
(Outside the main function)
float temperature_reading;
float *p_temperature_reading= &temperature_reading;
float humidity_reading;
float *p_humidity_reading= &humidity_reading;
The function I have working with the float, that I can save to a global variable
void MIA_get_current_temperature()
{
const char *query = "SELECT Temperature, Humidity FROM `temperature` WHERE Type='Current_Temperature'";
if (mysql_query(conn, query) != 0)
{
fprintf(stderr, "%s\n", mysql_error(conn));
exit(-1);
} else {
MYSQL_RES *query_results = mysql_store_result(conn);
if (query_results)
{ // make sure there *are* results..
MYSQL_ROW row;
while((row = mysql_fetch_row(query_results)) !=0)
{
float f = row[0] ? atof(row[0]) : 0.0f;
float h = row[1] ? atof(row[1]) : 0.0f;
*p_temperature_reading = f;
*p_humidity_reading = h;
printf("The Temp & Hum from DB is: %.1f & %.1f\n", *p_temperature_reading,*p_humidity_reading);
}
/* Free results when done */
mysql_free_result(query_results);
}
}
}
This is the function I can not get to work:
(Outside main Function)
char ac_mode[256];
char *p_ac_mode = &ac_mode[256];
Function:
void MIA_get_desired_temperature()
{
const char *query = "SELECT Mode, Desired_Temperature, Threshold FROM `ac_mode` WHERE Status='ON'";
if (mysql_query(conn, query) != 0)
{
fprintf(stderr, "%s\n", mysql_error(conn));
exit(-1);
} else {
MYSQL_RES *query_results = mysql_store_result(conn);
if (query_results)
{ // make sure there *are* results..
MYSQL_ROW row;
while((row = mysql_fetch_row(query_results)) !=0)
{
char *ac = row[0] ? row[0] : "NULL";
float desired_temperature = row[1] ? atof(row[1]) : 0.0f;
int threshold = row[2] ? atof(row[2]) : 0.0f;
*p_ac_mode = *ac;
*p_desired_temperature = desired_temperature;
*p_threshold=threshold;
}
/* Free results when done */
mysql_free_result(query_results);
}
}
}
char *ac is where I want the string to be stored.
This line:
char *p_ac_mode = &ac_mode[256];
..is incorrect. You're probably trying to declare a pointer to the array (or maybe to its contents)... what you're actually doing is declaring a char * that points at the first byte after the array ac_mode. The [256] here isn't indicating that ac_mode has 256 elements, it's indexing the array to get element 256 (which would be the 257th char in the array if it were big enough -- but it's not, so it's outside the array). You're then taking the address of that out-of-bounds char and assign it to p_ac_mode, so that p_ac_mode to points to it.
To point p_ac_mode at the array contents, you'd just use char *p_ac_mode = ac_mode; (which makes it a char * pointing at the first char in the array). To get a pointer to the array itself, you'd use char (*p_ac_mode)[256] = &ac_mode;, which makes it a pointer to a 256-element array of char. In any case there's no need for p_ac_mode at all, because you can access the array through ac_mode directly in all the same places, and the bare array name ac_mode will usually decay to a pointer to its first char anyway.
With this line:
*p_ac_mode = *ac;
..you're copying the first char from string ac to the first char after ac_mode (because that's what p_ac_mode points to, as explained above). I suspect you're actually trying to assign the whole ac string's contents to ac_mode via p_ac_mode -- but that won't work for a few reasons.
An array is actually a block of memory holding a series of values of the same type. Although in many situations the array name will decay to a pointer (the address of the array's first element), the array itself is the block of memory and not the pointer. You can't just assign a pointer (new address) to the array, and array contents aren't automatically copied this way either. The contents need to be copied over element by element, or using a function that copies the contents.
What you need to do is copy the contents of the string from your query results into the ac_mode array with strcpy() or similar. Just changing this line:
*p_ac_mode = *ac;
to this:
strcpy(ac_mode, ac);
...would do that.
You need to use strcpy in your MIA_get_desired_temperature function. Also, you don't need the pointer p_ac_mode. Just copy into ac_mode directly.
strcpy(ac_mode, ac);

Difference between call by name and call by text parameter passing mechanism with examples

Out of 5 types of parameter passing mechanism:
1.pass-by-value
2.pass-by-reference
3.pass-by-value-result
4.pass-by-text (macros in C)
5.pass-by-name (something like continuations)
I just want the difference between the last two.Please help !!
Reference: http://www.math.grin.edu/~rebelsky/Courses/CS302/99S/Outlines/outline.36.html
Call-by-text is where the function arguments are not evaluated before they are passed and are then substituted for the instances of the parameters. The arguments are passed "as text" and can hence cause problems if the local bound of the function use the same variable names outside the scope.
int i = 0;
void f(int j) {
print(j); // is replaced with print(i + 5) and prints 5
int i = 20;
print(j); // is replaced with print(i + 5) and prints 25
}
f(i + 5); // passes the unevaluated expression i + 5
Call-by-name is similar in that the function arguments are not evaluated before they are passed and are then substituted for the instances of the parameters. However, the parameters are bound to thunks, which act as a closure for variables within the scope of the calling function.
void f(int j) {
print(j); // prints 5
print(j); // prints 10
}
int i = 0;
f(i + 5); // passes the unevaluated expression i + 5
More information can be found here: http://www.cs.sjsu.edu/~pearce/modules/projects/Jedi/params/index.htm

What's the difference between call by reference and copy/restore

What's the difference in the outcome between call by reference and copy/restore?
Background: I'm currently studying distributed systems. Concerning the passing of reference parameters for remote procedure calls, the book states that: "the call by reference has been replaced by copy/restore. Although this is not always identical, it is good enough". I understand how call by reference and copy/restore work in principle, but I fail to see where a difference in the result may be?
Examples taken from here.
Main code:
#include <stdio.h>
int a;
int main() {
a = 3;
f( 4, &a );
printf("%d\n", a);
return 0;
}
Call by Value:
f(int x, int &y){
// x will be 3 as passed argument
x += a;
// now a is added to x so x will be 6
// but now nothing is done with x anymore
a += 2*y;
// a is still 3 so the result is 11
}
Value is passed in and has no effect on the value of the variable passed in.
Call by Reference:
f(int x, int &y){
// x will be 3 as passed argument
x += a;
// now a is added to x so x will be 6
// but because & is used x is the same as a
// meaning if you change x it will change a
a += 2*y;
// a is now 6 so the result is 14
}
Reference is passed in. Effectively the variable in the function is the same as the one outside.
Call with Copy/Restore:
int a;
void unsafe(int x) {
x= 2; //a is still 1
a= 0; //a is now 0
}//function ends so the value of x is now stored in a -> value of a is now 2
int main() {
a= 1;
unsafe(a); //when this ends the value of a will be 2
printf("%d\n", a); //prints 2
}
Value is passed in and has no effect on the value of the variable passed in UNTIL the end of the function, at which point the FINAL value of the function variable is stored in the passed in variable.
The basic difference between call by reference and copy/restore then is that changes made to the function variable will not show up in the passed in variable until after the end of the function while call by reference changes will be seen immediately.
Call by Copy/Restore is a special case of call-by-reference where the provided reference is unique to the caller. The final result on the referenced values will not be saved until the end of the function.
This type of calling is useful when a method in RPC called by reference. The actual data is sent to the server side and the final result will send to the client. This will reduce the traffic, since the server will not update the reference each time.
Call By Reference:
In call-by-reference, we pass a pointer to the called function. Any changes that happens to the data pointed by that pointer will be reflected immediately.
Suppose if there are numerous changes to be made to that data, while it wouldn’t incur much cost locally, it’ll be expensive in terms of network cost as for each change data will have to be copied back to the client.
C Code:
void addTwo(int *arr, int n){
for(int i=0;i<n;i++){
arr[i]+=2; //change is happening in the original data as well
}
}
int main(){
int arr[100]={1,2,3,...}; // assuming it to be initialised
addTwo(arr,100);
}
Call By Copy/Restore:
In call-by-copy/restore, the idea is that when the function is called with the reference to the data, only the final result of the changes made to the data is copied back to the original data(when the function is about to return) without making any changes to the original data during the function call, requiring only one transfer back to the client.
In the C code below, the data pointed by arr is copied in the function and stored back to arr after all the changes to the local data are finalised.
C Code:
void addTwo(int *arr, int n){
// copy data locally
larr = (int*)malloc(n*sizeof(int));
for(int i=0;i<n;i++){
larr[i]=arr[i];
}
for(int i=0;i<n;i++){
// change is happening to the local variable larr
larr[i]+=2;
}
//copy all the changes made to the local variable back to the original data
for(int i=0;i<n;i++){
arr[i]=larr[i];
}
}
int main(){
int arr[100]={1,2,3,...}; // assuming it to be initialised
addTwo(arr,100);
}
Note: Code shown above doesn’t represent actual RPC implementation, just an illustration of the concepts. In real RPC, complete data is passed in the message instead of pointers(addresses).