Page 4 of 6
Posted: Fri Mar 04, 2005 5:09 am
Thank you so much

Well, to be serious, OK, I will think about your hint, as it is
really a sort of hint Although a quite quite small hint.

Posted: Sun Mar 06, 2005 2:01 am
Larry, thank you for the small hint.
Although I knew it even before I started implementing some code
that we SHOULD NOT pre-generate all the primes up to 2^32 - 1.
It was pretty obvious.

Now I've designed a decent algorithm for solving this problem.
Although not the best one, of course.

So thank you, anyway.

### 10139 WA~~

Posted: Sun Mar 20, 2005 5:29 pm

Code: Select all

``````    Cut after AC
``````

Posted: Sun Mar 20, 2005 7:33 pm
Try this test case:

Code: Select all

``31 402653184``
The answer must be "does not divide," since:

31! = 2^26 3^14 ... 29^1 31^1
402653184 = 2^27 3^1

Posted: Mon Mar 21, 2005 2:57 am
Well~~Thx~~

I finally got AC~~

### 10139 Better Algorithm ?

Posted: Mon May 30, 2005 8:32 am
Hi
I tried solving Problem: 10139 but got a Time Limit Exceeded error.
What I was doing was, starting from n, i was calculating the gcd(n,m) and dividing m by gcd(n,m).

Code: Select all

`` m = m/gcd (m,n)  ``
then i did the same with n-1, and so on, till m was reduced to 1, or n became 1.

Sometimes, one gets a large prime number as one of the factors, and to handle that i counted the no. of times that the gcd was consecutively 1. In case, this exceeded 50 times, I checked if m was prime, and if it was, exited with a negative answer.

This works fine on almost all inputs, and comes out pretty fast when i try it on my system, but always gives TLE on the programming-challenges website.
the code is here

Code: Select all

``````#include <iostream.h>
#include <math.h>

long  gcd (long p,long q)
{
if (q == 0) return p;
else return (gcd (q, p%q));
}

bool isprime (long n)
{

for (int i = 3; i<=sqrt(n)+1 ; i+=2)
{
if (n%i == 0) {return (false);}
}
return (true);
}

int main()
{
do{
long n,m,saven, savem;
cin >>n>> m;
saven = n; savem = m;
bool flag = false;
int counter= 0;  //prime check
if (n == 0 && m == 1) {flag = true;goto End;}
if (n==0 && m>1) {flag = false;goto End;}
if (m == 0) {flag = false;goto End;}

// to c if m divides n!62454TK

while ( n >= 1 && m >= 1)
{
if (m <= n) { flag = true; goto End;}
long g = gcd (m,n);

if (g==1) { counter++; if (counter == 50)
{ if (isprime (m)) {flag = false;break;}}
}
else counter = 0;

m = m/g; n = (n - 1)*(n/g);
//cout << "n =" << n << " m = " << m << endl; //int x ; cin >> x;
if (m == 1) { flag = true; break; }
}

End:
if (flag == true) cout << savem <<" divides " << saven<<"!";
else              cout << savem <<" does not divide " << saven<<"!";
cout << endl;
} while (true);
return (0);
}

``````
Can u plz suggest a better algo to solve this problem. I have tried looking my Number Theory books, but am still in the dark regarding this problem. I would be really grateful if u could help me out.
Thanks,
CJ

### Re: 10139 Better Algorithm ?

Posted: Mon May 30, 2005 10:42 am
CodeJerk wrote:

Code: Select all

``````do{
...
} while (true);``````
I think it's the endless loop that gives you TLE.

### But is there an end condition?

Posted: Mon May 30, 2005 2:56 pm
The question doesnt specify any end condition, like, for e.g., that the last input is 0 0, which is *not* to be processed.
If u got AC could you plz tell me what was the end condition u specified.
CJ

Posted: Mon May 30, 2005 3:36 pm
Read until you hit EOF.Something along the line of...

Code: Select all

`````` while ( 2 == scanf("%d %d", &a, &b) ) {
}
``````
Regards,
Suman.

### 10139 Factovisors WA plz help

Posted: Wed Oct 05, 2005 12:47 pm
#include<cstdio>
#include<string>
#include<cmath>
using namespace std;
//FILE *in=fopen("fact.in","r");
bool iscom[46502];
int prime[5000];
#ifdef __GNUC__
#define longlong long long
#else
#define longlong __int64
#endif
int howfac(longlong* n,int f)
{
//return how many factor F is in n
longlong ret=0;
while(((*n)%f)==0)
{
(*n)/=f;
ret++;
}
return ret;
}
int main()
{
longlong i,j,k,n,m,c=0,f,x,y,m2,div;
memset(iscom,0,sizeof(iscom));
for(i=2;i<=46350;i++)
{
if(!iscom)
{
prime[c]=i;
c++;
for(j=(i+i);j<=46500;j+=i)
iscom[j]=1;
}
}
//while(EOF!=fscanf(in,"%lld %lld",&n,&m))
while(EOF!=scanf("%lld %lld",&n,&m))
{
m2=m;
if(n>=m)
div=1;
else if(m==0)
div=0;
else if(n==0)
div=1;
else
{
f=1;
for(i=0;i<c && prime*prime<=m;i++) //check if M is prime
if(m%prime==0){f=0;break;}

if(f)
div=0;
else
for(i=0;i<c;i++) //check if all prime factors in M is in N! with enough quantity
{
k=howfac(&m,prime);
if(k==0)continue;
x=0;
for(j=prime;j<=n;j+=prime)
{
y=j;
x+=howfac(&y,prime);
if(x>=k)
break;
}
if(x<k)
{div=0;break;}
if(m==1)
{div=1; break;}
}
}
if(!div)
printf("%lld does not divide %lld!\n",m2,n);
else
printf("%lld divides %lld!\n",m2,n);
}
return 0;
}

If any body can find a mistake or a bug plz tell me I hope that the comments will clarify my algorithm

### Accepted

Posted: Wed Oct 05, 2005 8:10 pm
I just rewrote the code and I got Accepted thx anyway

### 10139 - Factovisor why TLE

Posted: Sat Jul 01, 2006 7:11 am
Never mind it. Found the bug.
Thanx anyway to those who tried to help me.

Posted: Tue Oct 10, 2006 9:23 am
Thanks a lot.There was a silly mistake in my code and the test case 94764610 284293833 helped me finding that.

Posted: Wed Oct 11, 2006 11:15 pm
You can get the prime factors of the m and n (from two to n since it is n!) numbers and keep dividing out the prime factors from m until no more prime factors remain in m (return true) or until you reach n (return false).

I would not do it with BigInteger though because it seems the judge does not accept the BigInteger class. I got a compile error before on the Square root problem when I tried to use BigInteger, so I had to write my own BigInteger class.

Posted: Wed Mar 28, 2007 8:50 am
i am in great problem!
please say me why RE [signal 11]?

Code: Select all

``````

#include <stdio.h>
#include <string.h>

void str_mul(char str1[],int n );
long is_divisible(char str[],long);
char *x;
main()
{
char str[2600];
char res[1001][2600];
long num,fact,temp;

x = str;
strcpy(res[0],"1");
fact = 1;
strcpy(str,"1");
while(fact!=1001)
{
x = str;
str_mul(str,fact);
strcpy(res[fact],str);
fact = fact + 1;
}
while(scanf("%ld %ld",&fact,&num)==2)
{
temp = fact;
if(!is_divisible(res[fact],num))
printf("%ld divides %ld!\n",num,temp);
else
printf("%ld does not devide %ld!\n",num,temp);
}
return 0;
}

void str_rev(char *str)
{
long len,i;
char *p,*q,temp;
len = strlen(str);
p = str;
q = &str[len-1];
for(i=0;i<len/2;i++)
{
temp = *p;
*p = *q;
*q = temp;
p++;
q--;
}
}

void str_mul(char str1[], int n)
{
char *p;
char res[10000],tem[10000];
int len1,carry,i,j,temp;
len1 = strlen(str1);
str_rev(str1);
carry=0;
memset(res,'0',sizeof(res));
p = res;
for(i=0;i<len1;i++)
{
carry = 0;
p = &res[i];
int t = n;
while(t)
{
int a = str1[i]-48;
int b = t%10;
temp = *p-48 + carry+ (a*b);
*p = (*p-48 + carry + (a*b))%10 + 48;
carry=(temp/10);

p++;
t/=10;
}
if(carry)
*p = carry + 48;
}
if(carry)
p++;
*p = '\0';
for(i=strlen(res)-1;i>=0;i--)
{
*x = res[i];
x++;
}
*x = '\0';
}

long is_divisible(char p[], long num)
{
long mod=0;
long len,i;
len = strlen(p);
for(i=0;i<=len-1;i++)
mod=((p[i]-48)+mod*10)%num;
return (mod%num);
}

``````