cant understand the calculation of return statement of binary program with recursion in c - function

Program of binary conversion with recursion
it is working fine but i cant understand the meaning of one statement
Can any one help me to explain following
return (num % 2) + 10 * binary_conversion(num / 2);
while having input of 13
i am lil confused getting like this num =13;
13%2 = 1 + 10 * 6 = 66 , something stupid like calculation
int binary_conversion(int);
int main()
{
int num, bin;
printf("Enter a decimal number: ");
scanf("%d", &num);
bin = binary_conversion(num);
printf("The binary equivalent of %d is %d\n", num, bin);
}
int binary_conversion(int num)
{
if (num == 0)
{
return 0;
}
else
{
return (num % 2) + 10 * binary_conversion(num / 2);
}
}

Your confusions stems from not understanding the operation of recursion. It's time to interview the function with print statements. This will allow you to follow the control and data flow of the routine.
int binary_conversion(int num)
{
printf("ENTER num = %d\n", num);
if (num == 0)
{
printf("BASE CASE returns 0\n");
return 0;
}
else
{
printf("RECURSION: new bit = %d, recur on %d\n", num % 2, num / 2);
return (num % 2) + 10 * binary_conversion(num / 2);
}
}

Related

How to pass struct containing matrices in Cuda

As the titles says , i'm trying to pass a struct containing 4 matrices to a Cuda Kernel. The problem is that i get no errors, but the program crashes goes nuts whenever i try to execute it.All of the values returned are 0 and the clock value overflows.
Here's what i've made so far :
#define ROWS 700
#define COLS 1244
struct sobel {
int Gradient[ROWS][COLS];
int Image_input[ROWS][COLS];
int G_x[ROWS][COLS];
int G_y[ROWS][COLS];
};
__global__ void sobel(struct sobel* data)
{
int x = blockIdx.x * blockDim.x + threadIdx.x;
int y = blockIdx.y * blockDim.y + threadIdx.y;
int XLENGTH = ROWS;
int YLENGTH = COLS;
if ((x < XLENGTH) && (y < YLENGTH))
{
if (x == 0 || x == XLENGTH - 1 || y == 0 || y == YLENGTH - 1)
{
data->G_x[x][y] = data->G_y[x][y] = data->Gradient[x][y] = 0;
}
else
{
data->G_x[x][y] = data->Image_input[x + 1][y - 1]
+ 2 * data->Image_input[x + 1][y]
+ data->Image_input[x + 1][y + 1]
- data->Image_input[x - 1][y - 1]
- 2 * data->Image_input[x - 1][y]
- data->Image_input[x - 1][y + 1];
data->G_y[x][y] = data->Image_input[x - 1][y + 1]
+ 2 * data->Image_input[x][y + 1]
+ data->Image_input[x + 1][y + 1]
- data->Image_input[x - 1][y - 1]
- 2 * data->Image_input[x][y - 1]
- data->Image_input[x + 1][y - 1];
data->Gradient[x][y] = abs(data->G_x[x][y]) + abs(data->G_y[x][y]);
if (data->Gradient[x][y] > 255) {
data->Gradient[x][y] = 255;
}
}
}
}
int main() {
struct sobel* data = (struct sobel*)calloc(sizeof(*data), 1);
struct sobel* dev_data;
cudaMalloc((void**)&dev_data, sizeof(*data));
cudaMemcpy(dev_data, data, sizeof(data), cudaMemcpyHostToDevice);
dim3 blocksize(16, 16);
dim3 gridsize;
gridsize.x = (ROWS + blocksize.x - 1) / blocksize.x;
gridsize.y = (COLS + blocksize.y - 1) / blocksize.y;
sobel <<< gridsize, blocksize >>> (dev_data);
cudaMemcpy(data, dev_data, sizeof(data), cudaMemcpyDeviceToHost);
free(data);
cudaFree(dev_data);
return 0;
}
Do i also have to allocate device memory for each obe of the matrices ?
Any advice would be appreciated.
Edit : I switched a couple of things here but the program seems to ignore the nested else statement and all the values returned are 0 .
There (at least) are 2 errors in your code.
You have not allocated a correct size for the device struct:
cudaMalloc((void**)&dev_data, sizeof(data));
^
just like you did in your calloc call, that should be sizeof(*data) not sizeof(data) (Both cudaMemcpy calls should probably be updated to reflect this size as well.)
You need a proper thread check in your kernel code, something like this:
if (( x < XLENGTH ) && ( y < YLENGTH )){ // add this line
if (x == 0 || x == XLENGTH - 1 || y == 0 || y == YLENGTH - 1)
{
data->G_x[x][y] = data->G_y[x][y] = data->Gradient[x][y] = 0;
Without that, your next if test line may allow out-of-bounds threads to participate in the zeroing operation. For example any thread where x == 0 will pass that if-test. But that thread may have an out-of-bounds y-value.

How to add up all the date leading to a specific date entered by the user?

#include <iostream>
#include <string>
#include <cmath>
using namespace std;
int total(int month, int days, int years);
bool leap();
int numdays(int month, int years);
int main()
{
int month;
int days;
int year;
cout << "Enter the Date like mm-dd-yyyy:\n";
cin >> month >> days >> year;
while (month <= 0 || month >= 13 || days <= 0 || days >= 32 || year < 1000)
{
cout << "You entered invalid information. Please re-enter date with a legitimate date:\n ";
cin >> month >> days >> year;
}
total(month, days, year);
return 0;
}
bool leap(int y)
{
if ((y % 4 == 0 && y % 100 != 0) || (y % 400 == 0))
return true;
}
int total(int m, int d, int y)
{
int total = 0;
for (int i = 1; i < m; i++)
total = total + numdays(i, y);
total = total + d;
return total;
}
int numdays(int m, int y)
{
switch (m)
{
case 9:
case 4:
case 6:
case 11:
return 30;
case 2:
if (leap(y))
return 29;
else`enter code here`
return 28;
default:
return 31;
}
}
The point of this code is to add up all the days in the year up to the specific day that the user enter. For some reason after I enter the date and such the code just stops running. I'm not sure if I'm calling the functions correctly or if I'm not sending the right data to the functions. If anyone can help that would be appreciated.
It does not receive the return value of the call to total, and then print it, so that could make it appear to just stop running.
As an aside, leap should return false for non-leap years.

An error with dec to bin

I have been debugging this function but I don't know why is it throwing 99 when I send 4 to the function.
This is a function to covert from decimal to binary.
Actually, I have tried to cout exp, res and the other variables in each step and then multiply them but I don't know. It doesn't make sense.
int DecToBinary(long num) {
if(num == 0) {
return 0;
}
else if(num == 1) {
return 1;
}
int exp = 0;
int res = 0;
for (; num != 0; exp++){
res = res+num%2*pow(10,exp);
num = num/2;
}
return res;
}
Thank you guys.
if(num == 0) {
return 0;
}
else if(num == 0) {
return 1;
}
You know the second branch will never be executed, right?
Furthermore:
pow(10,exp);
this yields a floating-point number. Be prepared for rounding errors. Even better: don't use pow() at all (you don't need floating-point numbers for working with integers). Simply do the division step by step, accumulating the result in a variable.
int dec2bin(int n)
{
int r = 0, tp = 1;
while (n) {
r += (n % 2) * tp;
n >>= 1;
tp *= 10;
}
return r;
}

Implementing the exponential function with basic arithmetic operations

For the purpose of the exercise, I have to implement the exponential function with the most basic arithmetic operations. I came up with this, where x is the base and y the exponent:
function expAetB() {
product=1;
for (i=0; i<y; i++)
{
product=product*x;
}
return product;
};
However, there are more basic operations than product=product*x;. I should somehow be able to insert instead another for loop which multiply and pass the result, but I can't find a way to do it without falling into an infinite loop.
In the same way that exponentiation is repeated multiplication, so multiplication is simply repeated addition.
Simply create another function mulAetB which does that for you, and watch out for things like negative inputs.
You could go even one more level and define adding in terms of increment and decrement, but that may be overkill.
See, for example, the following program which uses the overkill method of addition:
#include <stdio.h>
static unsigned int add (unsigned int a, unsigned int b) {
unsigned int result = a;
while (b-- != 0) result++;
return result;
}
static unsigned int mul (unsigned int a, unsigned int b) {
unsigned int result = 0;
while (b-- != 0) result = add (result, a);
return result;
}
static unsigned int pwr (unsigned int a, unsigned int b) {
unsigned int result = 1;
while (b-- != 0) result = mul (result, a);
return result;
}
int main (void) {
int test[] = {0,5, 1,9, 2,4, 3,5, 7,2, -1}, *ip = test;
while (*ip != -1) {
printf ("%d + %d = %3d\n" , *ip, *(ip+1), add (*ip, *(ip+1)));
printf ("%d x %d = %3d\n" , *ip, *(ip+1), mul (*ip, *(ip+1)));
printf ("%d ^ %d = %3d\n\n", *ip, *(ip+1), pwr (*ip, *(ip+1)));
ip += 2;
}
return 0;
}
The output of this program shows that the calculations are correct:
0 + 5 = 5
0 x 5 = 0
0 ^ 5 = 0
1 + 9 = 10
1 x 9 = 9
1 ^ 9 = 1
2 + 4 = 6
2 x 4 = 8
2 ^ 4 = 16
3 + 5 = 8
3 x 5 = 15
3 ^ 5 = 243
7 + 2 = 9
7 x 2 = 14
7 ^ 2 = 49
If you really must have it in a single function, it's a simple matter of refactoring the function call to be inline:
static unsigned int pwr (unsigned int a, unsigned int b) {
unsigned int xres, xa, result = 1;
// Catch common cases, simplifies rest of function (a>1, b>0)
if (b == 0) return 1;
if (a == 0) return 0;
if (a == 1) return 1;
// Do power as repeated multiplication.
result = a;
while (--b != 0) {
// Do multiplication as repeated addition.
xres = result;
xa = a;
while (--xa != 0)
result = result + xres;
}
return result;
}

How to simplify this loop?

Considering an array a[i], i=0,1,...,g, where g could be any given number, and a[0]=1.
for a[1]=a[0]+1 to 1 do
for a[2]=a[1]+1 to 3 do
for a[3]=a[2]+1 to 5 do
...
for a[g]=a[g-1]+1 to 2g-1 do
#print a[1],a[2],...a[g]#
The problem is that everytime we change the value of g, we need to modify the code, those loops above. This is not a good code.
Recursion is one way to solve this(although I was love to see an iterative solution).
!!! Warning, untested code below !!!
template<typename A, unsigned int Size>
void recurse(A (&arr)[Size],int level, int g)
{
if (level > g)
{
// I am at the bottom level, do stuff here
return;
}
for (arr[level] = arr[level-1]+1; arr[level] < 2 * level -1; arr[level]++)
{
recurse(copy,level+1,g);
}
}
Then call with recurse(arr,1,g);
Imagine you are representing numbers with an array of digits. For example, 682 would be [6,8,2].
If you wanted to count from 0 to 999 you could write:
for (int n[0] = 0; n[0] <= 9; ++n[0])
for (int n[1] = 0; n[1] <= 9; ++n[1])
for (int n[2] = 0; n[2] <= 9; ++n[2])
// Do something with three digit number n here
But when you want to count to 9999 you need an extra for loop.
Instead, you use the procedure for adding 1 to a number: increment the final digit, if it overflows move to the preceding digit and so on. Your loop is complete when the first digit overflows. This handles numbers with any number of digits.
You need an analogous procedure to "add 1" to your loop variables.
Increment the final "digit", that is a[g]. If it overflows (i.e. exceeds 2g-1) then move on to the next most-significant "digit" (a[g-1]) and repeat. A slight complication compared to doing this with numbers is that having gone back through the array as values overflow, you then need to go forward to reset the overflowed digits to their new base values (which depend on the values to the left).
The following C# code implements both methods and prints the arrays to the console.
static void Print(int[] a, int n, ref int count)
{
++count;
Console.Write("{0} ", count);
for (int i = 0; i <= n; ++i)
{
Console.Write("{0} ", a[i]);
}
Console.WriteLine();
}
private static void InitialiseRight(int[] a, int startIndex, int g)
{
for (int i = startIndex; i <= g; ++i)
a[i] = a[i - 1] + 1;
}
static void Main(string[] args)
{
const int g = 5;
// Old method
int count = 0;
int[] a = new int[g + 1];
a[0] = 1;
for (a[1] = a[0] + 1; a[1] <= 2; ++a[1])
for (a[2] = a[1] + 1; a[2] <= 3; ++a[2])
for (a[3] = a[2] + 1; a[3] <= 5; ++a[3])
for (a[4] = a[3] + 1; a[4] <= 7; ++a[4])
for (a[5] = a[4] + 1; a[5] <= 9; ++a[5])
Print(a, g, ref count);
Console.WriteLine();
count = 0;
// New method
// Initialise array
a[0] = 1;
InitialiseRight(a, 1, g);
int index = g;
// Loop until all "digits" have overflowed
while (index != 0)
{
// Do processing here
Print(a, g, ref count);
// "Add one" to array
index = g;
bool carry = true;
while ((index > 0) && carry)
{
carry = false;
++a[index];
if (a[index] > 2 * index - 1)
{
--index;
carry = true;
}
}
// Re-initialise digits that overflowed.
if (index != g)
InitialiseRight(a, index + 1, g);
}
}
I'd say you don't want nested loops in the first place. Instead, you just want to call a suitable function, taking the current nesting level, the maximum nesting level (i.e. g), the start of the loop, and whatever if needs as context for the computation as arguments:
void process(int level, int g, int start, T& context) {
if (level != g) {
for (int a(start + 1), end(2 * level - 1); a < end; ++a) {
process(level + 1, g, a, context);
}
}
else {
computation goes here
}
}