C-greatest prime factor of a given number - c

I have written the following code to compute the greatest prime factor of a number supplied
through standard input but it is taking ages to execute.How can i reduce the execution time of the program?
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
bool is_prime(unsigned long long num)
{
if (num == 0 || num == 1)
return false;
if (num == 2)
return true;
for (unsigned long long j = 2; j < num; j++)
if(num%j==0)
return false;
return true;
}
int main(void)
{
unsigned long long n,i;
printf("enter the number: ");
scanf("%llu",&n);
for(i=n-1;i>1;i--)
if((is_prime(i)) && n%i==0)
break;
printf("%llu\n",i);
return 0;
}
Number in the input is 600851475143.

bool is_prime(unsigned long long num)
{
if (num < 2) return false; /* Reject border cases */
if (num == 2) return true; /* Accept the largest even prime */
if ((num & (~1)) == num) return false; /* Reject all other evens */
unsigned long long limit = sqrt(num) + 1; /* Limit the range of the search */
for (unsigned long long j = 3; j < limit; j += 2) /* Loop through odds only */
if(num % j==0)
return false; /* Reject factors */
return true; /* No factors, hence it is prime */
}

Have fun...one function for all prime factors, one for maximum prime factor:
#include <stdio.h>
#include <stdlib.h>
typedef unsigned long long u64_t;
static size_t prime_factors(u64_t value, u64_t *array)
{
size_t n_factors = 0;
u64_t n = value;
u64_t i;
while (n % 2 == 0)
{
n /= 2;
//printf("Factor: %llu (n = %llu)\n", 2ULL, n);
array[n_factors++] = 2;
}
while (n % 3 == 0)
{
n /= 3;
//printf("Factor: %llu (n = %llu)\n", 3ULL, n);
array[n_factors++] = 3;
}
for (i = 6; (i - 1) * (i - 1) <= n; i += 6)
{
while (n % (i-1) == 0)
{
n /= (i-1);
//printf("Factor: %llu (n = %llu)\n", (i-1), n);
array[n_factors++] = (i-1);
}
while (n % (i+1) == 0)
{
n /= (i+1);
//printf("Factor: %llu (n = %llu)\n", (i+1), n);
array[n_factors++] = (i+1);
}
}
if (n != 1)
array[n_factors++] = n;
return n_factors;
}
static u64_t max_prime_factor(u64_t value)
{
u64_t n = value;
u64_t i;
u64_t max = n;
while (n % 2 == 0)
{
n /= 2;
//printf("Factor: %llu (n = %llu)\n", 2ULL, n);
max = 2;
}
while (n % 3 == 0)
{
n /= 3;
//printf("Factor: %llu (n = %llu)\n", 3ULL, n);
max = 3;
}
for (i = 6; (i - 1) * (i - 1) <= n; i += 6)
{
while (n % (i-1) == 0)
{
n /= (i-1);
//printf("Factor: %llu (n = %llu)\n", (i-1), n);
max = (i-1);
}
while (n % (i+1) == 0)
{
n /= (i+1);
//printf("Factor: %llu (n = %llu)\n", (i+1), n);
max = (i+1);
}
}
//printf("Max Factor = %llu\n", (n == 1) ? max : n);
return (n == 1) ? max : n;
}
static void print_factors(u64_t value, size_t n_factors, u64_t *factors)
{
printf("%20llu:", value);
int len = 21;
for (size_t i = 0; i < n_factors; i++)
{
if (len == 0)
len = printf("%.21s", "");
len += printf(" %llu", factors[i]);
if (len >= 60)
{
putchar('\n');
len = 0;
}
}
if (len > 0)
putchar('\n');
}
void builtin_tests(void)
{
u64_t tests[] =
{
1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18,
19, 20, 25, 49, 63, 69, 71, 73, 825, 829, 1000, 6857, 73112,
731122, 7311229, 73112293, 731122935, 7311229357, 73112293571,
600851475143, 731122935711, 7311229357111,
18446744073709551610ULL, 18446744073709551611ULL,
18446744073709551612ULL, 18446744073709551613ULL,
18446744073709551614ULL, 18446744073709551615ULL,
};
u64_t factors[64];
for (size_t i = 0; i < sizeof(tests)/sizeof(tests[0]); i++)
{
u64_t max = max_prime_factor(tests[i]);
printf("%20llu -> Max Prime Factor = %llu\n", tests[i], max);
size_t n_factors = prime_factors(tests[i], factors);
print_factors(tests[i], n_factors, factors);
}
}
int main(int argc, char **argv)
{
if (argc == 1)
builtin_tests();
else
{
for (int i = 1; i < argc; i++)
{
u64_t factors[64];
u64_t value = strtoull(argv[i], 0, 0);
u64_t max = max_prime_factor(value);
printf("%20llu -> Max Prime Factor = %llu\n", value, max);
size_t n_factors = prime_factors(value, factors);
print_factors(value, n_factors, factors);
}
}
return 0;
}
Results
1 -> Max Prime Factor = 1
1:
2 -> Max Prime Factor = 2
2: 2
3 -> Max Prime Factor = 3
3: 3
4 -> Max Prime Factor = 2
4: 2 2
5 -> Max Prime Factor = 5
5: 5
6 -> Max Prime Factor = 3
6: 2 3
7 -> Max Prime Factor = 7
7: 7
8 -> Max Prime Factor = 2
8: 2 2 2
9 -> Max Prime Factor = 3
9: 3 3
10 -> Max Prime Factor = 5
10: 2 5
11 -> Max Prime Factor = 11
11: 11
12 -> Max Prime Factor = 3
12: 2 2 3
13 -> Max Prime Factor = 13
13: 13
14 -> Max Prime Factor = 7
14: 2 7
15 -> Max Prime Factor = 5
15: 3 5
16 -> Max Prime Factor = 2
16: 2 2 2 2
17 -> Max Prime Factor = 17
17: 17
18 -> Max Prime Factor = 3
18: 2 3 3
19 -> Max Prime Factor = 19
19: 19
20 -> Max Prime Factor = 5
20: 2 2 5
25 -> Max Prime Factor = 5
25: 5 5
49 -> Max Prime Factor = 7
49: 7 7
63 -> Max Prime Factor = 7
63: 3 3 7
69 -> Max Prime Factor = 23
69: 3 23
71 -> Max Prime Factor = 71
71: 71
73 -> Max Prime Factor = 73
73: 73
825 -> Max Prime Factor = 11
825: 3 5 5 11
829 -> Max Prime Factor = 829
829: 829
1000 -> Max Prime Factor = 5
1000: 2 2 2 5 5 5
6857 -> Max Prime Factor = 6857
6857: 6857
73112 -> Max Prime Factor = 37
73112: 2 2 2 13 19 37
731122 -> Max Prime Factor = 52223
731122: 2 7 52223
7311229 -> Max Prime Factor = 24953
7311229: 293 24953
73112293 -> Max Prime Factor = 880871
73112293: 83 880871
731122935 -> Max Prime Factor = 89107
731122935: 3 5 547 89107
7311229357 -> Max Prime Factor = 7311229357
7311229357: 7311229357
73112293571 -> Max Prime Factor = 8058227
73112293571: 43 211 8058227
600851475143 -> Max Prime Factor = 6857
600851475143: 71 839 1471 6857
731122935711 -> Max Prime Factor = 4973625413
731122935711: 3 7 7 4973625413
7311229357111 -> Max Prime Factor = 12939061
7311229357111: 547 1033 12939061
18446744073709551610 -> Max Prime Factor = 1504703107
18446744073709551610: 2 5 23 53301701 1504703107
18446744073709551611 -> Max Prime Factor = 287630261
18446744073709551611: 11 59 98818999 287630261
18446744073709551612 -> Max Prime Factor = 2147483647
18446744073709551612: 2 2 3 715827883 2147483647
18446744073709551613 -> Max Prime Factor = 364870227143809
18446744073709551613: 13 3889 364870227143809
18446744073709551614 -> Max Prime Factor = 649657
18446744073709551614: 2 7 7 73 127 337 92737 649657
18446744073709551615 -> Max Prime Factor = 6700417
18446744073709551615: 3 5 17 257 641 65537 6700417

The if statement in the loop in main() should check n%i==0 first so that non-factors are not checked for primeness. This alone makes the program over 200 times faster on all the numbers from 1 to 2000 on a simple test case I ran on a modern Intel CPU. The mod below just to main() (I broke it out into a function returning the largest prime factor) improves the speed significantly more. I also consider the number itself as a possible factor (not done in the original).
unsigned long long largest_prime_factor(unsigned long long n)
{
unsigned long long i,sqrtn,maxprime;
if (is_prime(n))
return(n);
sqrtn=(unsigned long long)sqrt((double)n);
maxprime=1;
for (i=2;i<=sqrtn;i++)
{
if (n%i==0)
{
unsigned long long f;
f=n/i;
if (is_prime(f))
return(f);
if (is_prime(i))
maxprime=i;
}
}
return(maxprime);
}

keeping the same logic you can reduce time by executing loop till sqrt(num) only.
because if it is not prime, there would be at least one divisor which is less then sqrt(num).
Let's take num is not prime. so for some 1< a < num, a*b = num.
so either a or b should be less than sqrt(num).
Hence your code be for is_prime should be changed to the one as follows
bool is_prime(unsigned long long num)
{
if (num == 0 || num == 1)
return false;
if (num == 2)
return true;
long long root_num = sqrt(num);
for (unsigned long long j = 2; j < root_num; j++)
if(num%j==0)
return false;
return true;
}
Now if you want to change your logic, then there is an algorithm called sieve method which finds all prime numbers which are less than given number. check this out Sieve Algorithm

Its better to start for loop from square root of number to 3,
again you can skip even numbers.
so that you can get answer within small time..

Related

kaprekar number calculation fails for more than two digits

why is the code not working? i cant get a valid output. Please help me to find whether the input is a Kaprekar number or not.I think i made it too complicated. Any suggestions for a simple method??
For example:
9 is a Kaprekar number since 9² = 81 & 8+1=9.
297 is a Kaprekar number since 297² = 88209 & 88+209 = 297. Below is the code.
Here is the code:
#include <stdio.h>
int main() {
int n, a, temp, length, sum = 0, s, i, rem, temp1, length1, sum1[10], sum2[10];
printf("n");
scanf("%d", &n);
a = n * n;
printf("%d\n", a);
temp = a;
length = 0;
while (temp > 0) {
length++;
temp = temp / 10;
}
temp1 = n;
length1 = 0;
while (temp1 > 0) {
length1++;
temp1 = temp1 / 10;
}
if (length1 == 1) {
for (i = 0; i < length; i++) {
rem = a % 10;
sum = sum + rem;
a = a / 10;
}
if (sum == n) {
printf("Kaprekar number");
} else {
printf("not a kaprekar number");
}
}
if (length1 > 1) {
s = length / 2;
for (i = 0; i < s; i++) {
printf("%d\n", sum1[i]);
}
for (i = s; i < length; i++) {
printf("%d\n", sum2[i]);
}
for (i = 0; i < length; i++) {
sum3[i] = sum1[i] + sum2[i];
}
}
return 0;
}
Here's my suggestion to simplify your code, and hopefully make it easier to debug.
Define a function that returns the number of digits.
Define a function that divides the square into to numbers, given the number of digits in the original number.
Compute the sum of the divided parts of the square and compare it with the original number.
int getNumberOfDigits(int n)
{
if ( n == 0 )
{
return 1;
}
int count = 0;
while ( n / 10 > 0 )
{
n /= 10;
++count;
}
return count;
}
void divideSquare(int square, int originalDigitCount, int out[2])
{
int left = square;
int right = 0;
for ( int = 0; i < originalDigitCount; ++i )
{
right = right*10 + left%10;
left /= 10;
}
out[0] = left;
out[1] = right;
}
int main()
{
for (int n = 0; n < 10000; ++n )
{
int square = n * n;
int out[2];
int count = getNumberOfDigits(n);
divideSquare(square, count, out);
if ( out[0] + out[1] == n )
{
printf("%d is a Kaprekar number\n", n);
}
}
}
According to this Wikipedia article, Kaprekar numbers are defined this way:
In mathematics, a non-negative integer is called a Kaprekar number for a given base if the representation of its square in that base can be split into two parts that add up to the original number, with the proviso that the part formed from the low-order digits of the square must be non-zero, although it is allowed to include leading zeroes. For instance, 45 is a Kaprekar number, because 452 = 2025 and 20 + 25 = 45. The number 1 is Kaprekar in every base, because 12 = 01 in any base, and 0 + 1 = 1. Kaprekar numbers are named after D. R. Kaprekar.
Your method seems too complicated and broken beyond repair. Here is a simpler approach:
square the number. I would recommend using a larger type such as unsigned long long to avoid arithmetic overflow during this computation.
iterate in a loop, dividing the square by increasing powers of 10 until the dividend is smaller than 10. If the remainder is non zero and the sum of the quotient and dividend of the square divided by the power of 10 equals the original number, you have a Kaprekar number.
Here is a simple implementation:
#include <stdio.h>
int test_kaprekar(unsigned long long n) {
unsigned long long quo, rem, pow10, square = n * n;
int i;
for (i = 1, pow10 = 10;; i++, pow10 *= 10) {
quo = square / pow10;
rem = square % pow10;
if (quo + rem == n && rem != 0) {
printf("%llu is a Kaprekar number: %llu*%llu = %llu, %llu+%.*llu = %llu\n",
n, n, n, square, quo, i, rem, n);
return 1;
}
if (quo < 10)
break;
}
return 0;
}
int main() {
unsigned long long i, start = 0, stop = 4294967295, count = 0;
for (i = start; i <= stop; i++) {
count += test_kaprekar(i);
}
printf("%llu Kaprekar numbers between %llu and %llu\n", count, start, stop);
return 0;
}
Output:
1 is a Kaprekar number: 1*1 = 1, 0+1 = 1
9 is a Kaprekar number: 9*9 = 81, 8+1 = 9
45 is a Kaprekar number: 45*45 = 2025, 20+25 = 45
55 is a Kaprekar number: 55*55 = 3025, 30+25 = 55
99 is a Kaprekar number: 99*99 = 9801, 98+01 = 99
297 is a Kaprekar number: 297*297 = 88209, 88+209 = 297
703 is a Kaprekar number: 703*703 = 494209, 494+209 = 703
999 is a Kaprekar number: 999*999 = 998001, 998+001 = 999
2223 is a Kaprekar number: 2223*2223 = 4941729, 494+1729 = 2223
2728 is a Kaprekar number: 2728*2728 = 7441984, 744+1984 = 2728
4879 is a Kaprekar number: 4879*4879 = 23804641, 238+04641 = 4879
4950 is a Kaprekar number: 4950*4950 = 24502500, 2450+2500 = 4950
5050 is a Kaprekar number: 5050*5050 = 25502500, 2550+2500 = 5050
5292 is a Kaprekar number: 5292*5292 = 28005264, 28+005264 = 5292
7272 is a Kaprekar number: 7272*7272 = 52881984, 5288+1984 = 7272
7777 is a Kaprekar number: 7777*7777 = 60481729, 6048+1729 = 7777
9999 is a Kaprekar number: 9999*9999 = 99980001, 9998+0001 = 9999
17344 is a Kaprekar number: 17344*17344 = 300814336, 3008+14336 = 17344
22222 is a Kaprekar number: 22222*22222 = 493817284, 4938+17284 = 22222
38962 is a Kaprekar number: 38962*38962 = 1518037444, 1518+037444 = 38962
77778 is a Kaprekar number: 77778*77778 = 6049417284, 60494+17284 = 77778
82656 is a Kaprekar number: 82656*82656 = 6832014336, 68320+14336 = 82656
95121 is a Kaprekar number: 95121*95121 = 9048004641, 90480+04641 = 95121
99999 is a Kaprekar number: 99999*99999 = 9999800001, 99998+00001 = 99999
...
86358636 is a Kaprekar number: 86358636*86358636 = 7457814011780496, 74578140+11780496 = 86358636
88888888 is a Kaprekar number: 88888888*88888888 = 7901234409876544, 79012344+09876544 = 88888888
91838088 is a Kaprekar number: 91838088*91838088 = 8434234407495744, 84342344+07495744 = 91838088
94520547 is a Kaprekar number: 94520547*94520547 = 8934133805179209, 89341338+05179209 = 94520547
99999999 is a Kaprekar number: 99999999*99999999 = 9999999800000001, 99999998+00000001 = 99999999
234567901 is a Kaprekar number: 234567901*234567901 = 55022100179545801, 55022100+179545801 = 234567901
243902440 is a Kaprekar number: 243902440*243902440 = 59488400237953600, 5948840+0237953600 = 243902440
332999667 is a Kaprekar number: 332999667*332999667 = 110888778222110889, 110888778+222110889 = 332999667
432432432 is a Kaprekar number: 432432432*432432432 = 186997808245434624, 186997808+245434624 = 432432432
567567568 is a Kaprekar number: 567567568*567567568 = 322132944245434624, 322132944+245434624 = 567567568
665188470 is a Kaprekar number: 665188470*665188470 = 442475700620940900, 44247570+0620940900 = 665188470
667000333 is a Kaprekar number: 667000333*667000333 = 444889444222110889, 444889444+222110889 = 667000333
765432099 is a Kaprekar number: 765432099*765432099 = 585886298179545801, 585886298+179545801 = 765432099
867208672 is a Kaprekar number: 867208672*867208672 = 752050880792003584, 75205088+0792003584 = 867208672
909090909 is a Kaprekar number: 909090909*909090909 = 826446280826446281, 82644628+0826446281 = 909090909
999999999 is a Kaprekar number: 999999999*999999999 = 999999998000000001, 999999998+000000001 = 999999999
1111111111 is a Kaprekar number: 1111111111*1111111111 = 1234567900987654321, 123456790+0987654321 = 1111111111
1776299581 is a Kaprekar number: 1776299581*1776299581 = 3155240201460775561, 315524020+1460775561 = 1776299581
2020202020 is a Kaprekar number: 2020202020*2020202020 = 4081216201612080400, 408121620+1612080400 = 2020202020
2646002646 is a Kaprekar number: 2646002646*2646002646 = 7001330002639001316, 7001330+002639001316 = 2646002646
3846956652 is a Kaprekar number: 3846956652*3846956652 = 14799075482367049104, 1479907548+2367049104 = 3846956652
3888938889 is a Kaprekar number: 3888938889*3888938889 = 15123845682376554321, 1512384568+2376554321 = 3888938889
4090859091 is a Kaprekar number: 4090859091*4090859091 = 16735128102417346281, 1673512810+2417346281 = 4090859091
4132841328 is a Kaprekar number: 4132841328*4132841328 = 17080377442424803584, 1708037744+2424803584 = 4132841328
110 Kaprekar numbers between 0 and 4294967295
All powers of 10 minus 1 are Kaprekar numbers in base 10, other Kaprekar numbers are quite rare around log10(n) between 10n and 10n+1.
There are a few mistakes with your code, for once you haven't initialized arrays of sum1 and sum2 which you use for printing and adding. secondly, array sum3[] isn't defined. also if your numbers are more than 2,147,483,647 which means you get an overflow if a is more than about 46340.
I was interested in the problem, so here's my implementation
#include <stdio.h>
#include <math.h>
int get_length(long long n){
int s = 0;
while (n>0){
s++;
n /= 10;
}
return s;
}
int is_kaprekar (long long n){
long long t, n2=n*n;
int i,s = get_length(n2);
t = pow(10,s);
for (i=0 ; i<s ; i++){
long long left,right;
left = n2/t;
right = n2%t;
if ((long long)(left+right) == n && left != t){
printf("%lld\n",n); // print n
printf("%lld\n",n2); // print n^2
printf("%lld\n",left);
printf("%lld\n",right);
printf("Kaprekar number\n");
return 1;
}
t/=10;
}
printf("not a kaprekar number");
return 0;
}
int main()
{
long long n,i,n2;
printf("n ");
scanf("%d",&n); // get n
is_kaprekar(n);
return 0;
}

How to get every digit from a number in C?

I have these variables:
int dividend;
 int divider;
And I have the function :
Divisibility7 (int num);
Those two variables will be at the main function, and the user will be asked to enter the dividend and divider, but in case the user enter the divider 7, then, the function above will be called.
The problem is that I have to follow specific criteria to do this. So let's say the user will enter with the dividend 7203. This happen :
I. Get the last digit of the number.
Last digit: 3
Ii. Multiply the last digit by 2
3 x 2 = 6
Iii. Get the value of the initial number, without the last digit.
720
Iv. Subtract the initial value without the last digit from the multiplication result.
fabs (720 - 6) = 714
V. Repeat the process until the result is a value less than or equal to 70
Vi. Compare the result with the table of contents (0, 7, 14, 21, 28, 35, 42, 49, 54, 63, 70) for
Determine whether or not the number is divisible by 7
Code :
int res;
int x;
int y;
int Divisibility7(int num) {
int res;
int x;
int y;
int z;
while(num > 70) {
x = num % 10; // get the last digit from the number
y = x * 2; // multiply the last digit by 2;
z = num/10; // get the first digits from the number
fabs(z - y); // subtract the first digits with the last digits;
}
}
In the part of the while, the final fabs(z-y) returns what I want, to be the first digits subtracting the last number, but the problem is that the while stop there, I have to do something to make this while go till 70 or less.
PS : I need to check if the final number from the iterations, it's a number multiplied by 7, how can I do that ? And I can't use mod for this.
You have not changed num in your while loop . Also you do no return the value . Hope the following code will be ok for you .
int Divisibility7(int num) {
int res,x,y,z;
while(num > 70) {
x = num % 10; // get the last digit from the number
y = x * 2; // multiply the last digit by 2;
z = num/10; // get the first digits from the number
num = abs(z - y); // subtract the first digits with the last digits;
}
if(num == 0 || num == 7 || num == 14 || num == 21 || num == 28 || num == 35 || num == 42 || num == 49 || num == 54 || num == 63 || num == 70) {
return 1;
}
else {
return 0;
}
}
Not sure, but I think this is what are you trying to do:
int main (void)
{
int number, lastDigitMultiplied;
scanf("%d", &number);
while(number > 70){
//get the last digit and multiply it by 2
lastDigitMultiplied = (number % 10) * 2;
//subtract the initial value without the last digit from the multiplication result.
number = number / 10 - lastDigitMultiplied;
}
if(abs(number) % 7 == 0)
printf("The result is %d and it is a multiple of 7", number);
else
printf("The result is %d and it is not a multiple of 7", number);
return 0;
}
for divisibility against 7, if you have a positive large bigint already formatted as a string, don't waste time with the regular method doing it 1 digit at a time.
powers of 10, mod 7, repeats every 6 rounds :
10^1 % 7 = 3 10^7 % 7 = 3 10^13 % 7 = 3
10^2 % 7 = 2 10^8 % 7 = 2 10^14 % 7 = 2
10^3 % 7 = 6 10^9 % 7 = 6 10^15 % 7 = 6
10^4 % 7 = 4 10^10 % 7 = 4 10^16 % 7 = 4
10^5 % 7 = 5 10^11 % 7 = 5 10^17 % 7 = 5
10^6 % 7 = 1 10^12 % 7 = 1 10^18 % 7 = 1
meaning, the effects of the digits mod 7 stay identical as long as they're in chunks of 6 digits at a time.
the largest multiple of 6-digits supported by double precision FP to full integer precision would be 12-digits at a time.
So the way to do it is to right-align the digits by padding leading edge zeros to ensure string length is a multiple of 12. Then simply add the digits onto each other, performing a single mod % 7 operation once every 9000 or so rounds of the addition loop
—- (that's when you run up against 2^53 limit; 9007 rounds if u wanna be pedantic about it)
example :
x = 71400535477047763120175175402859619447790
02233464423375355339031113233806609150957
x % 7 = 4
now try summing up chunks of 12 :
007140053547704776312017517540285961944779
002233464423375355339031113233806609150957
007140053547 7140053547
704776312017 711916365564
517540285961 1229456651525
944779002233 2174235653758
464423375355 2638659029113
339031113233 2977690142346
806609150957 3784299293303
----------------------------
3784299293303 % 7 = 4
it works exactly the same for any multiples of 6 : e.g. 6, 18, 24, and 30 --
00714005354770477631201751754
02859619447790022334644233753
55339031113233806609150957
312017 312017
517540 829557
285961 1115518
944779 2060297
002233 2062530
464423 2526953
375355 2902308
339031 3241339
113233 3354572
806609 4161181
150957 4312138
007140 4319278
053547 4372825
704776 5077601
----- -------
_ 5077601 % 7 = 4
00000000714005354770477631201
75175402859619447790022334644
23375355339031113233806609150957
464423375355339031 464423375355339031
113233806609150957 577657181964489988
000000007140053547 577657189104543535
704776312017517540 1282433501122061075
285961944779002233 1568395445901063308
---------------------------------------
1568395445901063308 % 7 = 4
00000000000000714005354770477
63120175175402859619447790022
33464423375355339031113233806
609150957
339031113233806609150957 339031113233806609150957
000000000000007140053547 339031113233813749204504
704776312017517540285961 1043807425251331289490465
944779002233464423375355 1988586427484795712865820
---------------------------------------------------
1988586427484795712865820 % 7 = 4
000000007140053547704776312017517
540285961944779002233464423375355
339031113233806609150957
000000007140053547704776312017 7140053547704776312017
517540285961944779002233464423 517540293101998326707009776440
375355339031113233806609150957 892895632133111560513618927397
892895632133111560513618927397 % 7 = 4

Project Euler 2# - strange output

I've tried to solve problem 2 on Project Euler in C. This is the first possible solution that came to my mind, and, in fact, it gives as an output the right answer. The problem is that each time I run my program it gives me a different output, which is either "2" or "4613732" that is the right answer. Sorry for my poor english, can you help me find out what's wrong?
#include <stdio.h>
int main(){
int n, n1 = 1, n2 = 2, sum = 2;
while(n<4000000){
n = n1 + n2; /*calculate the next number of the series*/
n1 = n2;
n2 = n;
if(n%2 == 0){
sum = sum + n; /*if the number it's even add it to the main sum*/
}
}
printf("The sum is %d\n", sum);
}
You didn't initialize n; when you get the right answer, it means you got lucky.
#include <conio.h>
#include <iostream>
using namespace std;
int evenFibSum(int i=1,int j=2)
{
const int max = 3999999;
int eventsum = 2;
int sum = 0;
while (sum < max)
{
sum = i + j;
i = j;
j = sum;
if (sum % 2 == 0)
eventsum +=sum;
}
return eventsum;
}
For more efficient solution apply following logic
Fibbonaci Series => 1 2 3 5 8 13 21 34 55 89 144
Index => 0 1 2 3 4 5 6 7 8 9 10
To get even fibbonanci addition I have to add following index values[1 4 7 10]
Here I am sensing some pattern
[1 4 7 10] => I need advance index by 3
so how to advance index by 3
// k = i+j = > 3 13 55
// i = k+j => 5 21 89
// j = k+i => 8 34 144
int evenFibSumx(int i=1,int j=2)
{
const int max = 3999999;
int eventsum = 2;
int k= 0;
while (1)
{
k = i + j;
i = k + j;
j = k + i;
if(i >= max)
break;
if (j%2 == 0)
eventsum +=j;
}
return eventsum;
}
int main()
{
std::cout << evenFibSum();
std::cout << evenFibSumx();
}

How to find Number of Factors of "product of numbers"

I m trying to find number of factors of product of big numbers.
The problem statement is this : Suppose you are given N numbers(let say N = 10), each number <= 1000000.
How to find the number of factors of the product of such numbers.
Can someone please provide an efficient algorithm for doing this.
Example :
1) N = 3 and Numbers are 3, 5, 7
Ans = 8 (1, 3, 5, 7, 15, 21, 35, 105)
2) N = 2 and Numbers are 5, 5
Ans = 3 (1, 5 and 25)
Editorial for the problem is here
http://discuss.codechef.com/questions/15943/numfact-editorial
int total = 0, N = 0, Number;
scanf ("%d", &total);
while (total--)
{
scanf ("%d", &N);
map<int, int> Counter;
for (int i = 0; i < N; i++)
{
scanf ("%d", &Number);
for (int j = 2; j * j <= Number; j++)
{
while (Number % j == 0)
{
Counter[j]++;
Number /= j;
}
}
if (Number > 1) Counter[Number]++;
}
int Answer = 1;
for (map<int, int>::iterator it = Counter.begin(); it != Counter.end(); it++)
Answer *= (it->second + 1);
printf ("%d\n", Answer);
}
This got Accepted.
Sample Inputs and Outputs:
7
3
3 5 7
3
2 4 6
2
5 5
10
2 2 2 2 2 2 2 2 2 2
1
100
10
10000 10000 10000 10000 10000 10000 10000 10000 10000 10000
10
1000000 1000000 1000000 1000000 1000000 1000000 1000000 1000000 1000000 1000000
8
10
3
11
9
1681
3721
Factorize each number into list of prime factors and their multiplicities, L(n) = { p_i , k_i }, for a number n = Π piki. Numer of divisors for such n is ND( L(n) ) = Π (ki+1) a product of all coefficients, each incremented by 1 (this includes 1 and n itself as divisors of n). This corresponds to picking none, one, ... ki of each of them to multiply.
To calculate the ND of a product of arbitrary number of numbers, factorize each and merge their factorizations, where in case of matching primes their coefficients are added together. Then calculate the ND of the merged factorization.
To merge many factorizations together, start by merging two of them; then merge the result and the next one; then merge the last result and the next factorization, and so on. This is called folding. Or better merge them pairwise, then merge the results in same pairwise fashion, and so on util only one merged result is left. That's similar to how a bottom-up mergesort is done.
Multiply all the numbers, factorize the result, count all divisors:
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
int main(int argc, char *argv[])
{
int p = 1;
for (int i = 1; i < argc; i++)
p *= strtol(argv[i], NULL, 10);
int n = 0;
int s = sqrt(p) + 1;
for (int i = 1; i <= s; i++)
if (p % i == 0)
n += 2 - (p / i == i); // obfuscation ;)
printf("%d\n", n);
return 0;
}

Count total number of digits from a given positive number without looping in C

How to count total number of digits from a given positive number without looping in C?
For integers, take the log10 of the number, round down, and add one.
TEST:
#include <math.h>
#include <stdio.h>
int
num_digits(unsigned long number)
{
return (int)(floor(log10((double)number)) + 1.0);
}
int
main(int argc, char **argv)
{
unsigned long test_numbers[] = {
1, 9, 10, 99, 100, 999, 1000, 9999, 10000, 99999, 100000, 999999,
123456789ul,
999999999ul,
0
};
unsigned long *ptr;
for(ptr = test_numbers; *ptr; ptr++)
{
printf("Number of digits in %lu: %d\n", *ptr, num_digits(*ptr));
}
return 0;
}
Output:
Number of digits in 1: 1
Number of digits in 9: 1
Number of digits in 10: 2
Number of digits in 99: 2
Number of digits in 100: 3
Number of digits in 999: 3
Number of digits in 1000: 4
Number of digits in 9999: 4
Number of digits in 10000: 5
Number of digits in 99999: 5
Number of digits in 100000: 6
Number of digits in 999999: 6
Number of digits in 123456789: 9
Number of digits in 999999999: 9
One possible solutions, assuming 16-bit integer values and logical expressions evaluating to 0 or 1. You could replace the conditions with (u > 99) ? 1 : 0 if you're worried about portability.
int digits( unsigned u)
{
return 1 + (u > 9) + (u > 99) + (u > 999) + (u > 9999);
}
Two solutions for you!
int digit_count(unsigned int n)
{
if (n < 10)
return 1;
else
return (1 + digit_count(n / 10));
}
and
unsigned int n = 50;
int i = 0;
HACK:
i++;
if (n < 10)
{
printf("Digits: %d\n", i);
}
else
{
n /= 10;
goto HACK;
}
Don't hate me for the last one :(
return snprintf(0, 0, "%d", num);

Resources