int j = 10;
void f() {
int *i;
i = &j;
*i = 7;
i = (int *) malloc(sizeof(int));
*i = j;
j = j + 5;
printf("%d %d", *i, j);
}
Write down the two values that the function f will output
I am not able to fully understand how pointers work
So this is my interpretation of the code
int j = 10;
J is assigned to value 10 in memory and has a address lets say 200
int *i;
declaring a pointer
i = &j;
i value is now 200
*i = 7
value of *i is 7
i = (int *) malloc(sizeof(int))
do not really understand what the above code is doing, but I think it assigns the variable i to the size of integer in array?
*i = j
Does *i point to address of j or the value of j
j = j + 5
the value of j (which I don't know what is) + 5
Thank you
First off, I'd recommend either reading a good C book or looking for a tutorial online to get some basics right.
int *i;
i = &j;
This makes pointer variable i to point to the same memory region where variable j resides (so your guess is right).
*i = 7;
Now, the location pointed to by i is updated to read 7. So, j is no longer 10, it's now 7 as *i and j are the same value.
i = (int *) malloc(sizeof(int));
Now, you allocated new piece of heap memory sufficient to hold a single int value. i no longer points to the location of j.
*i = j;
Set the value stored in location pointed to by i to have the same value as j, in this case 7.
j = j + 5;
Increment j by 5. Since i no longer points to &j the value stored in *i is unaffected.
printf("%d %d", *i, j);
Print value of *i and j.
As previously demonstrated i points to a memory location holding a value of 7 and j is 7 + 5 = 12.
Related
I have kernel which evaluate interaction between all pairs of neighbors of an atoms. Each atom has max. 4 neighbors so I store their indexes in int4. But in order to loop over these neighbors I need to access them by index (neighs[0] rather than neighs.x ).
The loop should look something like:
int iatom = get_global_id(0);
int4 ng = neighs[iatom]; // each atoms has 4 neighbors
float4 p0 = atom_pos[iatom];
float4 force = (float)(0.f,0.f,0.f,0.f);
for(int i=0; i<4; i++){
int ing = ng[i]; // HERE: index into vector
float4 pi = atom_pos[ing];
for(int j=i+1; j<4; j++){
int jng = ng[j]; // HERE: index into vector
float4 pj = atom_pos[jng];
force += evalInteraction( p0, pi, pj );
}
}
forces[iatom]=force;
I have some idea how it can be probably done but not sure:
Unroll the loops
since there are just 4*3/2=6 pair-interactions it would be probably even more efficient. But it would be much less readable and more difficult do modify.
cast int4 to int*
but is it fine ? Doesn't it break something? Doesn't it make some performance issue? I mean this:
int4 ng_ = neighs[iatom]; // make sure we copy it to local memory or register
int* ng = (int*)&ng_; // pointer to local memory can be optimized out, right ?
for(int i=0; i<4; i++){
int ing = ng[i];
...
}
You can cast directly, but you can also declare a union for easier access:
union
{
int components[4];
int4 vector;
} neighbors;
neighbors.vector = ng;
neighbors.components[i]; // Works now
I'm an amateur playing with discrete math. This isn't a
homework problem though I am doing it at home.
I want to solve ax + by = c for natural numbers, with a, b and c
given and x and y to be computed. I want to find all x, y pairs
that will satisfy the equation.
This has a similar structure to Bezout's identity for integers
where there are multiple (infinite?) solution pairs. I thought
the similarity might mean that the extended Euclidian algorithm
could help here. Below are two implementations of the EEA that
seem to work; they're both adapted from code found on the net.
Could these be adapted to the task, or perhaps can someone
find a more promising avenue?
typedef long int Int;
#ifdef RECURSIVE_EEA
Int // returns the GCD of a and b and finds x and y
// such that ax + by == GCD(a,b), recursively
eea(Int a, Int b, Int &x, Int &y) {
if (0==a) {
x = 0;
y = 1;
return b;
}
Int x1; x1=0;
Int y1; y1=0;
Int gcd = eea(b%a, a, x1, y1);
x = y1 - b/a*x1;
y = x1;
return gcd;
}
#endif
#ifdef ITERATIVE_EEA
Int // returns the GCD of a and b and finds x and y
// such that ax + by == GCD(a,b), iteratively
eea(Int a, Int b, Int &x, Int &y) {
x = 0;
y = 1;
Int u; u=1;
Int v; v=0; // does this need initialising?
Int q; // quotient
Int r; // remainder
Int m;
Int n;
while (0!=a) {
q = b/a; // quotient
r = b%a; // remainder
m = x - u*q; // ?? what are the invariants?
n = y - v*q; // ?? When does this overflow?
b = a; // A candidate for the gcd - a's last nonzero value.
a = r; // a becomes the remainder - it shrinks each time.
// When a hits zero, the u and v that are written out
// are final values and the gcd is a's previous value.
x = u; // Here we have u and v shuffling values out
y = v; // via x and y. If a has gone to zero, they're final.
u = m; // ... and getting new values
v = n; // from m and n
}
return b;
}
#endif
If we slightly change the equation form:
ax + by = c
by = c - ax
y = (c - ax)/b
Then we can loop x through all numbers in its range (a*x <= c) and compute if viable natural y exists. So no there is not infinite number of solutions the limit is min(c/a,c/b) ... Here small C++ example of naive solution:
int a=123,b=321,c=987654321;
int x,y,ax;
for (x=1,ax=a;ax<=c;x++,ax+=a)
{
y = (c-ax)/b;
if (ax+(b*y)==c) here output x,y solution somewhere;
}
If you want to speed this up then just iterate y too and just check if c-ax is divisible by b Something like this:
int a=123,b=321,c=987654321;
int x,y,ax,cax,by;
for (x=1,ax=a,y=(c/b),by=b*y;ax<=c;x++,ax+=a)
{
cax=c-ax;
while (by>cax){ by-=b; y--; if (!y) break; }
if (by==cax) here output x,y solution somewhere;
}
As you can see now both x,y are iterated in opposite directions in the same loop and no division or multiplication is present inside loop anymore so its much faster here first few results:
method1 method2
[ 78.707 ms] | [ 21.277 ms] // time needed for computation
75044 | 75044 // found solutions
-------------------------------
75,3076776 | 75,3076776 // first few solutions in x,y order
182,3076735 | 182,3076735
289,3076694 | 289,3076694
396,3076653 | 396,3076653
503,3076612 | 503,3076612
610,3076571 | 610,3076571
717,3076530 | 717,3076530
824,3076489 | 824,3076489
931,3076448 | 931,3076448
1038,3076407 | 1038,3076407
1145,3076366 | 1145,3076366
I expect that for really huge c and small a,b numbers this
while (by>cax){ by-=b; y--; if (!y) break; }
might be slower than actual division using GCD ...
Below is a piece of C code run from R used to compare each row of a matrix to a vector. The number of identical values is stored in the first column of a two-column matrix.
I know it can easily be done in R (as done to check the results), but this is a first step for a more complex use case.
When openmp is not used, it works ok. When openmp is used, it give correlated (0.99) but inconsistent results.
Question1: What am I doing wrong?
Question2: I use a double for loop to fill the output matrix (ret) with zeros. What would be a better solution?
Also, inconsistencies were observed when the code was used in a package. I tried to make the code reproducible using inline, but it does not recognize the openmp statements (I tried to include 'omp.h', in the parameters of cfunction, ...).
Question3: How can we make this code work with inline?
I'm (too?) far outside my comfort zone on this topic.
library(inline)
compare <- cfunction(c(x = "integer", vec = "integer"), "
const int I = nrows(x), J = ncols(x);
SEXP ret;
PROTECT(ret = allocMatrix(INTSXP, I, 2));
int *ptx = INTEGER(x), *ptvec = INTEGER(vec), *ptret = INTEGER(ret);
for (int i=0; i<I; i++)
for (int j=0; j<2; j++)
ptret[j * I + i] = 0;
int i, j;
#pragma omp parallel for default(none) shared(ptx, ptvec, ptret) private(i,j)
for (j=0; j<J; j++)
for (i=0; i<I; i++)
if (ptx[i + I * j] == ptvec[j]) {++ptret[i];}
UNPROTECT(1);
return ret;
")
N = 3e3
M = 1e4
m = matrix(sample(c(-1:1), N*M, replace = TRUE), nc = M)
v = sample(-1:1, M, replace = TRUE)
cc = compare(m, v)
cr = rowSums(t(t(m) == v))
all.equal(cc[,1], cr)
Thanks to the comments above, I reconsidered the data race issue.
IIUC, my loop was parallelized on j (the columns). Then, each thread had its own value of i (the rows), but possible identical values across threads, that were then trying to increment ptret[i] at the same time.
To avoid this, I now loop on i first, so that only a single thread will increment each row.
Then, I realized that I could move the zero-initialization of ptret within the first loop.
It seems to work. I get identical results, increased CPU usage, and 3-4x speedup on my laptop.
I guess that solves questions 1 and 2. I will have a closer look at the inline/openmp problem.
Code below, fwiw.
#include <omp.h>
#include <R.h>
#include <Rinternals.h>
#include <stdio.h>
SEXP c_compare(SEXP x, SEXP vec)
{
const int I = nrows(x), J = ncols(x);
SEXP ret;
PROTECT(ret = allocMatrix(INTSXP, I, 2));
int *ptx = INTEGER(x), *ptvec = INTEGER(vec), *ptret = INTEGER(ret);
int i, j;
#pragma omp parallel for default(none) shared(ptx, ptvec, ptret) private(i, j)
for (i = 0; i < I; i++) {
// init ptret to zero
ptret[i] = 0;
ptret[I + i] = 0;
for (j = 0; j < J; j++)
if (ptx[i + I * j] == ptvec[j]) {
++ptret[i];
}
}
UNPROTECT(1);
return ret;
}
Let’s consider you have a collection of N wines placed next to each other on a shelf. The price of the ith wine is pi. (prices of different wines can be different). Because the wines get better every year, supposing today is the year 1, on year y the price of the ith wine will be y*pi, i.e. y-times the value that current year.
You want to sell all the wines you have, but you want to sell exactly one wine per year, starting on this year. One more constraint - on each year you are allowed to sell only either the leftmost or the rightmost wine on the shelf and you are not allowed to reorder the wines on the shelf (i.e. they must stay in the same order as they are in the beginning).
You want to find out, what is the maximum profit you can get, if you sell the wines in optimal order?
int N; // number of wines
int p[N]; // array of wine prices
int cache[N][N]; // all values initialized to -1
int profit(int be, int en) {
if (be > en)
return 0;
if (cache[be][en] != -1)
return cache[be][en];
int year = N - (en-be+1) + 1;
return cache[be][en] = max(profit(be+1, en) + year * p[be],profit(be, en-1) + year * p[en]);
}
Time Complexity: O(n^2).
I have already found this O(n^2) solution. Can we do it in O(n) ? (Better time complexity)
You are supposed to find the optimal cost by selling all the wines from the shelf. And only the constraint is that you are allowed to pick only left or right wine(you can't pick a wine bottle from the middle of the shelf).
As we are allowed to pick the left or right wine, the optimal sequence of solution will include either left or right bottle.
Let's find a recursive solution for that.
Just pick-up the left bottle and calculate it's cost
pick-up the right bottle and calculate the cost
Compare both the cost and choose the maximum cost
Write the necessary condition for the base case
Let's write a c++ program for this--
#include<bits/stdc++.h>
using namespace std;
int max_cost(int wine[], int cost, int counter, int i, int j){
// Here `counter` keeps track of the number of years
// `i` is the left indices of the shelf
// `j` is the right indices of the shelf
// `cost` is the maximum cost that we have to find
if(i > j)
return cost;
else if(i == j){
cost += counter * wine[i];
return cost;
}
else{
int cost1 = counter * wine[i] + max_cost(wine, 0, counter + 1, i + 1, j);
int cost2 = counter * wine[j] + max_cost(wine, 0, counter + 1, i, j - 1);
cost += max(cost1, cost2);
return cost;
}
}
int main(){
int n;
cin >> n;
int wine[n];
for(int j = 0; j < n; ++j)
cin >> wine[j];
cout << max_cost(wine, 0, 1, 0, n - 1) << endl;
return 0;
}
I think the above code is self exlanatory
Let's run it:
Input1:
5
1
3
1
5
2
Output:
43
Input2:
4
10
1
10
9
Output:
79
The time complexity of above code is O(2^n), where n is the no. of wine bottles in the shelf.
Can we improvise the time complexity?
Ofcourse. We are basically calculating for some sequences again and again, which can be avoided by memorization technique.
The recurrence relation will be basically same. In addition to that, we will memorize the value for the specific i and j. And hence we will not have to calculate the value for the same i and j again and again.
The c++ code will be --
#include<bits/stdc++.h>
using namespace std;
int find_cost(vector<int>& box, vector<vector<int>>& dp, int i, int j){
if(i == j) // base case
dp[i][j] = box[i] * box.size();
else if(!dp[i][j]){ // If not calculated so far
int n = box.size();
dp[i][j] = max(find_cost(box, dp, i, j - 1) + box[j] * (n - (j - i)),
find_cost(box, dp, i + 1, j) + box[i] * (n - (j - i)));
}
return dp[i][j];
}
void cost_wine(vector<int> box){
int n = box.size();
vector<vector<int>> dp(n + 1, vector<int>(n + 1)); // Initialize dp array
cout << find_cost(box, dp, 0, n - 1);
return;
}
int main(){
int n;
cin >> n;
vector<int> box(n);
for(int i = 0; i < n; ++i)
cin >> box[i];
cost_wine(box);
return 0;
}
Now the time complexity of the above code would be O(n^2), which is far better than the recursion method.
I have a problem with Shuffling this array with Arduino software:
int questionNumberArray[10]={0,1,2,3,4,5,6,7,8,9};
Does anyone know a build in function or a way to shuffle the values in the array without any repeating?
The simplest way would be this little for loop:
int questionNumberArray[] = {0,1,2,3,4,5,6,7,8,9};
const size_t n = sizeof(questionNumberArray) / sizeof(questionNumberArray[0]);
for (size_t i = 0; i < n - 1; i++)
{
size_t j = random(0, n - i);
int t = questionNumberArray[i];
questionNumberArray[i] = questionNumberArray[j];
questionNumberArray[j] = t;
}
Let's break it line by line, shall we?
int questionNumberArray[] = {0,1,2,3,4,5,6,7,8,9};
You don't need to put number of cells if you initialize an array like that. Just leave the brackets empty like I did.
const size_t n = sizeof(questionNumberArray) / sizeof(questionNumberArray[0]);
I decided to store number of cells in n constant. Operator sizeof gives you number of bytes taken by your array and number of bytes taken by one cell. You divide first number by the second and you have size of your array.
for (size_t i = 0; i < n - 1; i++)
Please note, that range of the loop is n - 1. We don't want i to ever have value of last index.
size_t j = random(0, n - i);
We declare variable j that points to some random cell with index greater than i. That is why we never wanted i to have n - 1 value - because then j would be out of bound. We get random number with Arduino's random function: https://www.arduino.cc/en/Reference/Random
int t = questionNumberArray[i];
questionNumberArray[i] = questionNumberArray[j];
questionNumberArray[j] = t;
Simple swap of two values. It's possible to do it without temporary t variable, but the code is less readable then.
In my case the result was as follows:
questionNumberArray[0] = 0
questionNumberArray[1] = 9
questionNumberArray[2] = 7
questionNumberArray[3] = 4
questionNumberArray[4] = 6
questionNumberArray[5] = 5
questionNumberArray[6] = 1
questionNumberArray[7] = 8
questionNumberArray[8] = 2
questionNumberArray[9] = 3