Projecteuler 3 - largest prime number - c

I'm curious why this code doesn't find the largest prime factor.
I can't find the mathematic and/or logic mistake.
#include <stdio.h>
int compute( int input ) {
int biggest_primefactor = 1;
while(input > biggest_primefactor) {
int i = 2;
while(input%i != 0) i++; /* find factor, which is a primefactor */
input /= i;
if( i > biggest_primefactor) biggest_primefactor = i;
}
return biggest_primefactor;
}
void main () {
unsigned long long int input = 600851475143;
printf("%d", compute( input ));
}
Output is 1

Related

C code is giving zero value every time. What can I correct?

I am starter in the C.I wrote a simple code which are calculating how many digits are the entered Number and sum of entered number’s digits.Code calculating digit count right but sum of digits being given as ‘0’ every time.Could you say where is my error?thanks.
\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\
int ndigit(int val) {
if (val == 0)
return 0;
int digit_count = 1;
while ((val = getchar() != '\n')) {
digit_count++;
val /= 10;
}
return digit_count;
}
int sumdigit(int number) {
int result = 0;
while ((number = getchar()) != '\n'){
result += number - '0';
}
return result;
}
int main()
{
int a;
printf("Bir tam sayi giriniz: \n");
a = getchar();
printf("Bu sayinin basamak sayisi =%d", ndigit(a));
printf("Bu sayinin basamak degeri toplami= %d", sumdigit(a));
}
\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\
The program does not make sense. To enter a number you should use one function. That is the number of digits and the sum of digits must be calculated for the same number.
This condition in the while statement
while ((val = getchar() != '\n')) {
is equivalent to
while ( ( val = ( getchar() != '\n' ) ) ) {
and as a result the integer val gets either 1 or 0.
As the variable val stores an internal representation of a character (for example its ASCII value) then this statement
val /= 10;
also does not make sense. Also the user can enter a non-digit character.
You should either use a character array for the entered number by means of calls of the function getchar or use the function scanf to enter a value of an integer object.
If to use a character array then the program can look the following way
#include <stdio.h>
char * get_number( char *number, size_t n )
{
size_t i = 0;
int c;
while( i + 1 < n && ( c = getchar() ) != EOF && c != '\n' && '0' <= c && c <= '9' )
{
number[i++] = c;
}
number[i] = '\0';
return number;
}
size_t ndigit( const char *number )
{
size_t n = 0;
while ( number[n] != '\0' ) ++n;
return n;
}
unsigned int sumdigit( const char *number )
{
unsigned int sum = 0;
while ( *number != '\0' )
{
sum += *number++ - '0';
}
return sum;
}
int main(void)
{
enum { N = 50 };
char number[N];
printf( "Bir tam sayi giriniz: " );
get_number( number, N );
printf( "Bu sayinin basamak sayisi = %zu\n", ndigit( number ) );
printf( "Bu sayinin basamak degeri toplami = %u\n", sumdigit( number ) );
return 0;
}
The program output might look like
Bir tam sayi giriniz: 123456789987654321
Bu sayinin basamak sayisi = 18
Bu sayinin basamak degeri toplami = 90
If to use an integer number then the program can look the following way
#include <stdio.h>
size_t ndigit( unsigned long long number )
{
const unsigned long long Base = 10;
size_t n = 0;
do
{
++n;
} while ( number /= Base );
return n;
}
unsigned int sumdigit( unsigned long long number )
{
const unsigned long long Base = 10;
unsigned int sum = 0;
do
{
sum += number % Base;
} while ( number /= Base );
return sum;
}
int main(void)
{
unsigned long long number = 0;
printf( "Bir tam sayi giriniz: " );
scanf( "%llu", &number );
printf( "Bu sayinin basamak sayisi = %zu\n", ndigit( number ) );
printf( "Bu sayinin basamak degeri toplami = %u\n", sumdigit( number ) );
return 0;
}
The program output might look as it is shown above.
Bir tam sayi giriniz: 123456789987654321
Bu sayinin basamak sayisi = 18
Bu sayinin basamak degeri toplami = 90
You code has 3 getchar() that are independent. Just use one getchar, either in main, or ndigit or sumdigit.
I propose, you should get the number in main function using scanf instead of getchar(), then pass the number as the argument to the other functions (ndigit and sumdigit). Because getchar reads character by character, and it does not guarantee the character is a digit or not.
The main function becomes:
int main () {
int num;
printf("enter the number: ");
scanf("%d", &num);
// calling the ndigit and sumdigit function:
printf("sum of digits = %d\n number of digits = %d\n", sumdigit(num), ndigit(num));
return 0;
}
For two function ndigit and sumdigit, you can change to:
ndigit function:
int ndigit(int number) {
number = abs(number); // calculate abs if the number is negative
if(number == 0)
return 1;
int count = 0;
do {
count++;
num /= 10;
} while(num != 0);
return count;
}
sumdigit function:
int sumdigit(int number) {
number = abs(number); // calculate abs if the number is negative
int sum = 0, temp = 0;
while (number != 0) {
temp = number % 10;
sum += temp;
number /= 10;
}
return sum;
}
The complete code:
#include <stdio.h>
#include <stdlib.h>
int ndigit(int number) {
number = abs(number); // calculate abs if the number is negative
if(number == 0)
return 1;
int count = 0;
do {
count++;
number /= 10;
} while(number != 0);
return count;
}
int sumdigit(int number) {
number = abs(number); // calculate abs if the number is negative
int sum = 0, temp = 0;
while (number != 0) {
temp = number % 10;
sum += temp;
number /= 10;
}
return sum;
}
int main () {
int num;
printf("enter the number: ");
scanf("%d", &num);
// calling the ndigit and sumdigit function:
printf("sum of digits = %d\nnumber of digits = %d\n", sumdigit(num), ndigit(num));
return 0;
}
The output of test:
enter the number: 222333
sum of digits = 15
number of digits = 6
After using scanf, change your sumdigit while loop to:
while (number > 0) {
result += number % 10;
number /= 10;
}

how do I add up the sum of the digits of a number except for digits that repeat themselves in c?

I have an assignment and I need to add up the digits of it and ignore the once that repeat themselves
for example 234111 -> 2 + 3 + 4 + 1 -> 10
I tried doing this:
#include
int main(void)
{
int i = 0;
int num = 0;
int sum = 0;
printf("Please enter a number\n");
scanf("%d", &num);
while(num > 0){
sum += num%10;
num /= 10;
}
printf("%d", sum);
return 0;
}
what I did just adds up the digits, it doesn't ignore that ones that get repeated
What do i need to add to the code?
You can keep an array of 'flags' for which digits have been used already:
#include <stdio.h>
int main(void)
{
// int i = 0; // You don't actually use this in the code!
int num = 0;
int sum = 0;
int used[10] = { 0, }; // Set all "used" flags to zero
printf("Please enter a number\n");
scanf("%d", &num);
while (num > 0)
{
int digit = num % 10; // Get the digit
if (!used[digit]) sum += digit; // Only add if not used already
used[digit] = 1; // Now we have used it!
num /= 10;
}
printf("%d", sum);
return 0;
}
Feel free to ask for further clarification and/or explanation.
Just read each character and record if you've already seen it:
#include <stdio.h>
#include <ctype.h>
int
main(void)
{
int seen[10] = {0};
int sum = 0;
int c;
while( ( c = getchar()) != EOF ) {
int v = c - '0';
if( isspace(c)) {
continue;
}
if( v < 0 || v > 9 ) {
fprintf(stderr, "Invalid input\n");
return 1;
}
if( ! seen[v]++ )
sum += v;
}
printf("%d\n", sum);
return 0;
}

C Language Multiply Program wont work properly

My program gets a binary string ( up to 200 characters long) and then it multiplies it by a decimal number. The calculator works only for the first 2-3 iterations. After that it doesn't return the correct result. Any help ?
#include <stdio.h>
#include "myfun.c"
#include <string.h>
int main()
{
int l,l1;
char a[200],b[200],f[200];
int c[200],d[200];
for (i=0;i<200;i++)
{
c[i]=0;
d[i]=0;
}
gets(a);
l=strlen(a);
l1=strlen(a);
for (int i=0;i<l;i++)
{
c[200-l+i]=a[i]-48;
}
////////////////////////////////////////////
for (int i=0;i<l1;i++)
{
d[200-l1+i]=a[i]-48;
}
////////////////////////////////
for (int t=1;t<193;t++) //here is specify how many times i am multypling
bin_add(c,d);
for (i=0;i<200;i++){
printf("%d",c[i]);
}
return 0;
}
int bin_add(int c[200],int d[200])
{
int car[200]; //carry
i=200;
car[i]=0;
while (i >= 0) {
//find carry and shift it left
//find the sum
car[i-1] = c[i] & (d[i] |car[i]) ;
c[i]=(c[i]^d[i]) ^ car[i];
i--;
}
return c[i];
c[i]=0;
}

Recursive Persistence of a number

I am trying to find the persistence of a number. When you multiply the digits of a number together, eventually you will arrive at a single digit number. Persistence is the number of cycles that takes. I am trying to find that using a recursive Function. Here is my code:
#include <stdio.h>
int persistence(int x);
int main(int argc, char *argv[])
{
int x, per = 0, t;
char c;
while((c = getchar())!= EOF)
{
printf("Enter a number:\n");
scanf("%d", &x);
while(x>10)
{
t = persistence(x);
printf("\n%d", persistence(t));
per++;
}
printf("\n%d\n\n", per);
}
return 0;
}
int persistence(int x)
{
if(x<10)
{
return x;
}
else
{
return (x%10 * persistence(x/10));
}
}
The function persistence itself should return the value of the multiplicative persistence.
It can be defined the following way as it is shown in the demonstrative program.
#include <stdio.h>
size_t persistence( unsigned int x )
{
const unsigned int Base = 10;
if ( ! ( x < Base ) )
{
unsigned int n = 1;
do { n *= x % Base; } while ( x /= Base );
return 1 + persistence( n );
}
else
{
return 0;
}
}
int main(void)
{
unsigned int x = 39;
printf( "persistence( %u ) = %zu\n", x, persistence( x ) );
return 0;
}
The program output is
persistence( 39 ) = 3

I have to check a number is palindrome or not by recursion

int main()
{
int i,n;
printf("Enter the number");
scanf("%d",&n);
i=pali(n);
if(n==i)
printf("Number is pall");
else
printf("Not Pall");
}
int pali(int n)
{
int r;
static sum=0;
if(n!=0)
{
r=n%10;
sum=sum*10+r;
pali(n/10);
}
return sum;
}
I used a static variable to add up the sum. Is there any way where no static variable will be used?
Yes, the typical ("functional") approach is to carry the state in the form of a function argument. This often makes it necessary/nice to have a second function that does the actual recursion, which you can start by calling with the proper initial values for the state:
int do_pali(int sum, int n)
{
if(n != 0)
{
const int r = n % 10;
return do_pali(10 * sum + r, n / 10);
}
return sum;
}
the public function then just becomes:
int pali(int n)
{
return do_pali(0, n);
}
In languages with inner functions this can be more neatly expressed (GCC supports this as an extension).
Sure, you can do it this way :
#include <stdio.h>
int pali(int n)
{
int sum = 0;
int keeper = 0;
for (int i = n; i > 0; i /= 10) {
if (keeper != 0) {
sum *= 10;
sum += (keeper - i * 10);
}
keeper = i;
}
sum *= 10;
sum += keeper;
return sum;
}
int main(int argc, char** argv)
{
int i, n;
printf("Enter the number : ");
scanf("%d",&n);
i = pali(n);
if(n == i)
printf("Number is palindrome");
else
printf("Not Palindrome");
}
Using recursion is even easier :
#include <stdio.h>
int pali(int n, int sum)
{
sum += n - ((n / 10) * 10);
n /= 10;
if (n > 0)
pali(n, sum * 10);
else
return sum;
}
int main(int argc, char** argv)
{
int i, n;
printf("Enter the number : ");
scanf("%d",&n);
i = pali(n, 0);
if(n == i)
printf("Number is palindrome");
else
printf("Not Palindrome");
}
And a recursive version with only one parameter :
#include <stdio.h>
int pali(int n)
{
int fUnit, lUnit;
fUnit = n;
int mul = 1;
while (fUnit > 10) {
fUnit /= 10;
mul *= 10;
}
lUnit = n - ((n / 10) * 10);
n -= (fUnit * mul);
n /= 10;
if (mul == 1) return 1;
else if (fUnit == lUnit) return pali(n);
else return 0;
}
int main(int argc, char** argv)
{
int n;
printf("Enter the number : ");
scanf("%d",&n);
if(pali(n) == 1)
printf("Number is palindrome");
else
printf("Not Palindrome");
}
Since your function returns sum you could replace this line:
pali(n/10);
with
sum=pali(n/10);
You'd also have to move it up a line too.
Here is an optimized version that
Doesn't use local static.
Only includes stdio.h
Uses recursion.
#include <stdio.h>
static void perform_useless_recursion (int n)
{
if(n--)
{
perform_useless_recursion(n);
}
}
_Bool is_pali (int n)
{
perform_useless_recursion(1);
int sum = 0;
for(int i=n; i!=0; i/=10)
{
sum = sum*10 + i%10;
}
return n == sum;
}
int main (void)
{
int n=5005;
if(is_pali(n))
printf("Number is pall");
else
printf("Not Pall");
return 0;
}
The code could be improved even further by removing the perform_useless_recursion() function.
The advantage of this code is that the actual calculation is performed by a fast loop, instead of slow, dangerous recursion. In the real world outside artificial school assignments, there is no reason to write inefficient and dangerous code when you could write efficient and safe code. As a bonus, removing recursion also gives far more readable code.
If you benchmark this code you'll notice that it will be faster than all other versions posted and consumes less memory.
You can make a function that check only the first and the last digits of the number and pass the rest of the number onward.
To explain better, think about the following cases:
pali(1220) would check for the first (1) and last (0) digits. Since 1 != 0 pali would return false.
pali(17891) would check first (1) and last (1). Since they're equal then the function would recursively return pali(789) (which itself would return false since 7 != 9).
pali(878) would check that 8=8 and recursively return pali(7)
pali(3) would check that first (3) and last (3) numbers are equal and return 0.
The challenge here is to develop an algorithm that:
Check if first and last numbers are the same (even if it's only one digit!)
Strip the number from first and last digits and call itself on the remainder
Then all you need to do is apply recursion. Here's a sample implementation:
int pali(int number)
{
int smallDigit, bigDigit;
/* When recursion ends suceffuly*/
if (number == 0)
return 1;
/* Check for first and last digit of a number */
smallDigit = number % 10;
bigDigit = number;
while(bigDigit/10!=0)
{
bigDigit = bigDigit/10;
smallDigit = smallDigit*10;
}
/* Check to see if both digits are equal (Note: you can't use smallDigit here because it's been multiplied by 10 a few times) */
if (bigDigit != number%10)
return 0;
else
{
number = (number - smallDigit)/10; /* This is why smallDigit was multiplied by 10 a few times */
return pali(number); /* Recursion time */
}
}

Resources