Is there a better way to do this? Extracting numbers - c

I need to extract all the digits of a 16 digit number and need to store the as all different values, but I am repeating a lot of code. Is there a better way to do this?
it worked but I want to make it look nicer. I am a complete noob
int num1 = creditn % 10;
creditn /= 10;
int num2 = creditn % 10;
creditn /= 10;
int num3 = creditn % 10;
creditn /= 10;
int num4 = creditn % 10;
creditn /= 10;
int num5 = creditn % 10;
creditn /= 10;
int num6 = creditn % 10;
creditn /= 10;
int num7 = creditn % 10;
creditn /= 10;
int num8 = creditn % 10;
creditn /= 10;
int num9 = creditn % 10;
creditn /= 10;
int num10 = creditn % 10;
creditn /= 10;
int num11 = creditn % 10;
creditn /= 10;
int num12 = creditn % 10;
creditn /= 10;
int num13 = creditn % 10;
creditn /= 10;
int num14 = creditn % 10;
creditn /= 10;
int num15 = creditn % 10;
creditn /= 10;
int num16 = creditn % 10;
creditn /= 10;

As you could see, doing this without arrays is painful.
You probably need something like this:
int num[16]; // declare an array of 16 numbers,
// rather than 16 variables num1 to num16
for (int i = 0; i < 16; i++)
{
num[i] = credit % n;
credit /= n;
}

Related

Which for loops is totally correct for swapping two elements in C?

Both of them can run, but I think their logic are not same.
for (int i = 0; i < length; i++)
{
for (int j = i + 1; j < length; j++)
{
if (arr[i] > arr[j])
{
temp = arr[i];
arr[i] = arr[j];
arr[j] = temp;
}
}
}
or
for (int i = 0; i < length; i++)
{
for (int j = 0; j < length - i - 1; j++)
{
if (arr[j] > arr[j+1])
{
temp = arr[j];
arr[j] = arr[j+1];
arr[j+1] = temp;
}
}
}
Which one is totally correct for swapping two elements in C?
Logic for swapping is same in both the codes btw these codes does sorting. Swapping was just a step in sorting. Alternatively you can try
num1 = num1 ^ num2; //Using XOR operator
num2 = num1 ^ num2;
num1 = num1 ^ num2;
num1 = num1 + num2; //Using Add & Sub operator
num2 = num1 - num2;
num1 = num1 - num2;
num1 = num1 * num2; //Using Multiply & Divide operator
num2 = num1 / num2;
num1 = num1 / num2;

Implement a function named as flip; which will take a number as input and flip its last N digits

when I try to call the function as flip(flip(num,no),no). I am getting an answer of flip(num, no) and I can't find the solution of this code.
#include <stdio.h>
#include <math.h>
int flip(int number, int n);
main()
{
int num = 12345;
int no = 3;
int result = flip(flip(num,no), no);
printf("%d", result);
}
int flip(int number, int n)
{
int x = number % 10;
int s = n + x * pow(10, n - 1);
int temp = n * pow(10, n - 1) + x;
int sum = number + s - temp;
int* ptr = ∑
return *ptr;
}
Required Answer = 12345;
Output = 12543;
With loop, you can handle digit by digit:
int flip(int number, int n)
{
int rev = 0;
for (int i = 0; i != n; ++i) {
rev *= 10;
rev += number % 10;
number /= 10;
}
for (int i = 0; i != n; ++i) {
number *= 10;
}
return number + rev;
}
Demo

Getting a SIGSEGV error on codechef for this code

Im trying to submit a solution for the problem FCTRL2(https://www.codechef.com/problems/FCTRL2) on codechef. On executing the code it sometimes gets executed successfully while sometimes it gives a SIGSEGV error. But when I submit it, it always shows wrong answer. Though the code gives correct answer when i run it on any other IDE.
#include <iostream>
#include <stdio.h>
using namespace std;
int main(void)
{
int testCases, i, j, k, n, num, digits, carry = 0, temp;
scanf("%d", &testCases);
int testArr[160];
for (i = 0; i < testCases; i++)
{
scanf("%d", &n);
num = n;
if (n == 0 || n == 1)
{
testArr[0] = 1;
digits = 1;
}
else
{
k = 0;
for (j = 10; n != 0; j = j * 10)
{
testArr[k] = n % j;
n = n / j;
k++;
}
digits = k;
for (j = 1; j < num; j++)
{
for (k = 0; k < digits; k++)
{
temp = testArr[k] * j + carry;
if (temp > 10)
{
testArr[k] = temp % 10;
carry = temp / 10;
}
else
{
testArr[k] = temp;
carry = 0;
}
}
if (carry > 10)
{
testArr[k] = carry % 10;
k++;
testArr[k] = carry / 10;
digits = k + 1;
carry = 0;
}
else if (carry > 0)
{
testArr[k] = carry;
digits = k + 1;
carry = 0;
}
}
}
for (k = (digits - 1); k >= 0; k--)
{
printf("%d", testArr[k]);
}
printf("\n");
}
return 0;
}

Timing sum by column different arrays sizes and cache behaviour

I am using 2D array and 1D array to calculate the sum by row and column for array a and array s. The purpose is to calculate the sum of the 2D array a in the array s. N is the size of the array my question is why do we get significant change when we N=512 and N=1024 as shown in excel
/* sumcol_bycol: Basic implementation of column sum operation.
* Computes sums of the columns of array a into array s.
* s[c] = SUM(r=0..N-1) a[r][c]
*/
static void FN_ALIGN sumcol_bycol(int a[N][N], int s[N]) {
int r, c, sum;
// Iterate over all columns
for (c = 0; c < N; c++) {
// Compute the sum of data in column c
sum = 0;
for (r = 0; r < N; r++) {
sum += a[r][c];
}
// Return the sum in element c of array s
s[c] = sum;
}
}
/* Computing down columns with loop unrolling */
static void FN_ALIGN sumcol_bycol_u4(int a[N][N], int s[N]) {
int r, c, sum;
for (c = 0; c < N; c++) {
sum = 0;
for (r = 0; r < N-3; r+=4) {
sum += a[r][c];
sum += a[r+1][c];
sum += a[r+2][c];
sum += a[r+3][c];
}
/* The additional cases if unrolling factor does not divide N evenly */
# if N%4 >= 1
sum += a[r][c];
# endif
# if N%4 >= 2
sum += a[r+1][c];
# endif
# if N%4 >= 3
sum += a[r+2][c];
# endif
s[c] = sum;
}
}
/* Unrolling to a factor of 8 */
static void FN_ALIGN sumcol_bycol_u8(int a[N][N], int s[N]) {
int r, c, sum;
for (c = 0; c < N; c++) {
sum = 0;
for (r = 0; r < N-7; r+=8) {
sum += a[r][c];
sum += a[r+1][c];
sum += a[r+2][c];
sum += a[r+3][c];
sum += a[r+4][c];
sum += a[r+5][c];
sum += a[r+6][c];
sum += a[r+7][c];
}
# if N%8 >= 1
sum += a[r][c];
# endif
# if N%8 >= 2
sum += a[r+1][c];
# endif
# if N%8 >= 3
sum += a[r+2][c];
# endif
# if N%8 >= 4
sum += a[r+3][c];
# endif
# if N%8 >= 5
sum += a[r+4][c];
# endif
# if N%8 >= 6
sum += a[r+5][c];
# endif
# if N%8 >= 7
sum += a[r+6][c];
# endif
s[c] = sum;
}
}
/* Grouping: Compute two columns together */
static void FN_ALIGN sumcol_bycol_g2(int a[N][N], int s[N]) {
int r, c, sum0, sum1;
for (c = 0; c < N-1; c+=2) {
sum0 = sum1 = 0;
for (r = 0; r < N; r++) {
sum0 += a[r][c];
sum1 += a[r][c+1];
}
s[c] = sum0;
s[c+1] = sum1;
}
/* If there is an odd number of columns */
# if N%2 == 1
sum0 = 0;
for (r = 0; r < N; r++) {
sum0 += a[r][c];
}
s[c] = sum0;
# endif
}
/* Grouping 3 columns at once */
static void FN_ALIGN sumcol_bycol_g3(int a[N][N], int s[N]) {
int r, c, sum0, sum1, sum2;
for (c = 0; c < N-2; c+=3) {
sum0 = sum1 = sum2 = 0;
for (r = 0; r < N; r++) {
sum0 += a[r][c];
sum1 += a[r][c+1];
sum2 += a[r][c+2];
}
s[c] = sum0;
s[c+1] = sum1;
s[c+2] = sum2;
}
# if N%3 != 0
for ( ; c < N; c++) {
sum0 = 0;
for (r = 0; r < N; r++) {
sum0 += a[r][c];
}
s[c] = sum0;
}
# endif
}
/* Grouping 4 columns at once */
static void FN_ALIGN sumcol_bycol_g4(int a[N][N], int s[N]) {
int r, c, sum0, sum1, sum2, sum3;
for (c = 0; c < N-3; c+=4) {
sum0 = sum1 = sum2 = sum3 = 0;
for (r = 0; r < N; r++) {
sum0 += a[r][c];
sum1 += a[r][c+1];
sum2 += a[r][c+2];
sum3 += a[r][c+3];
}
s[c] = sum0;
s[c+1] = sum1;
s[c+2] = sum2;
s[c+3] = sum3;
}
# if N%4 != 0
for ( ; c < N; c++) {
sum0 = 0;
for (r = 0; r < N; r++) {
sum0 += a[r][c];
}
s[c] = sum0;
}
# endif
}
/* Grouping 5 columns at once */
static void FN_ALIGN sumcol_bycol_g5(int a[N][N], int s[N]) {
int r, c, sum0, sum1, sum2, sum3, sum4;
for (c = 0; c < N-4; c+=5) {
sum0 = sum1 = sum2 = sum3 = sum4 = 0;
for (r = 0; r < N; r++) {
sum0 += a[r][c];
sum1 += a[r][c+1];
sum2 += a[r][c+2];
sum3 += a[r][c+3];
sum4 += a[r][c+4];
}
s[c] = sum0;
s[c+1] = sum1;
s[c+2] = sum2;
s[c+3] = sum3;
s[c+4] = sum4;
}
# if N%5 != 0
for ( ; c < N; c++) {
sum0 = 0;
for (r = 0; r < N; r++) {
sum0 += a[r][c];
}
s[c] = sum0;
}
# endif
}
/* sumcol_byrow: Column sums computed using row-wise array access.
*/
static void FN_ALIGN sumcol_byrow(int a[N][N], int s[N]) {
int r, c, sum;
// Initialise all sums to zero.
for (c = 0; c < N; c++)
s[c] = 0;
// Iterate over all array elements, adding
// each one onto the appropriate sum.
for (r = 0; r < N; r++) {
for (c = 0; c < N; c++) {
s[c] += a[r][c];
}
}
}
/* Row-wise array access with loop unrolling */
static void FN_ALIGN sumcol_byrow_u4(int a[N][N], int s[N]) {
int r, c, sum;
for (c = 0; c < N; c++)
s[c] = 0;
for (r = 0; r < N; r++) {
for (c = 0; c < N-3; c+=4) {
s[c] += a[r][c];
s[c+1] += a[r][c+1];
s[c+2] += a[r][c+2];
s[c+3] += a[r][c+3];
}
# if N%4 >= 1
s[c] += a[r][c];
# endif
# if N%4 >= 2
s[c+1] += a[r][c+1];
# endif
# if N%4 >= 3
s[c+2] += a[r][c+2];
# endif
}
}
/* Row-wise computation using 2x2 blocks. The main loops are in 2x2 row-wise blocks
* then each block updates two sums */
static void FN_ALIGN sumcol_byrow_b2x2(int a[N][N], int s[N]) {
int r, c, sum;
for (c = 0; c < N; c++)
s[c] = 0;
for (r = 0; r < N-1; r+=2) {
for (c = 0; c < N-1; c+=2) {
s[c] += a[r][c] + a[r+1][c];
s[c+1] += a[r][c+1] + a[r+1][c+1];
}
# if N%2 != 0
s[c] += a[r][c] + a[r+1][c];
# endif
}
# if N%2 != 0
/* Process the remaining row */
for (c = 0; c < N-1; c+=2) {
s[c] += a[r][c];
s[c+1] += a[r][c+1];
}
/* Process the corner element */
s[c] += a[r][c];
# endif
}

Expanding the QR Decomposition of square matrices to tall matrices

I'm trying to convert the QR Decomposition from "Numerical Recipes in C" to work with skinny (tall) matrices. Does anyone know how to do this? I believe the problem lies in how the householder is multiplied with the A but I am unable to figure it out.
void qrdcmp(float **a, int n, float *c, float *d, int *sing)
{
int i,j,k;
float scale,sigma,sum,tau;
*sing=0;
for (k = 1; k < n; k++) {
scale = 0.0;
for (i = k; i <= n; i++) scale = FMAX(scale, fabs(a[i][k]));
if (scale == 0.0) { // Singular case.
*sing = 1;
c[k] = d[k] = 0.0;
} else { // Form Qk and Qk · A.
for (i = k; i <= n; i++) a[i][k] /= scale;
for (sum = 0.0, i = k; i <= n; i++) sum += SQR(a[i][k]);
sigma = SIGN(sqrt(sum), a[k][k]);
a[k][k] += sigma;
c[k] = sigma * a[k][k];
d[k] = -scale * sigma;
for (j = k + 1; j <= n; j++) {
for (sum = 0.0, i = k; i <= n; i++) sum += a[i][k] * a[i][j];
tau = sum / c[k];
for (i = k; i <= n; i++) a[i][j] -= tau * a[i][k];
}
}
}
d[n] = a[n][n];
if (d[n] == 0.0) *sing=1;
}

Resources