Bài 1: Cho số tự nhiên A. Hãy Tìm số tự nhiên N nhỏ nhất sao cho N lũy Thừa N (hân N cho chính nó N lần) chia hết cho A. Hãy viết chương trình tìm số N đó và xuất ra màn hình. Trong đó A có giá trị: 1 ≤ A ≤ 109
Ví dụ:
Số xuất ra là N
| |
8
|
4
|
13
|
13
|
Nhận xét: Bài toán đòi hỏi phải tìm số nguyên nhỏ nhất dạng NN chia hết cho số nguyên A được nhập vào từ bàn phím. Dễ thấy nếu N = A thì hiển nhiên AA chia hết cho A vì vậy ta luôn có N ≤ A. Trong trường hợp A nhỏ bài toán có thể dễ dàn giải quyết bằng cách duyệt từ 0 tới A, tính NN và kiểm tra điều kiện chia hết cho A.
Nhưng vấn đề của bài toán này là khi N lớn (xấp xỉ 1 tỉ) thì NN Có giá trị rất lớn mà không có một kiểu dữ liệu căn bản nào có thể chứa được. Vì vậy ở đây ta sẽ đi tìm một giải pháp khác mà không phải tính toán số cực lớn NN
Dễ thấy A luôn có thể phân tích thành tích lũy thừa các số nguyên tố A = p1x1 p2x2 … pkxk Do đó điều kiện cần để NN chia hết cho A là N chia hết cho tích T =p1p2 … pk (Ta có thể chứng minh điều này đễ dàn bằng phản chứng). Ta đăt N = T * i (i ≤ N) Khi đó NN = (T*i)T*i = TT*i * iT*i (với T = P1P2....Pk)
Ta tìm điều kiện đủ để NN chia hết cho A:
Gọi Xmax = MAX{x1, x2.....xn} khi đó nếu N= T*i ≥ Xmax lúc đó TT*i sẽ chia hết cho A vì vậy NN chia hết cho A. Vì T, Xmax luôn là hằng số với mỗi giá trị nhập vào của A ta sẽ có i ≥ Xmax \ T bài toán trở thành tìm giá trị nhỏ nhất của i thỏa mãn i ≥ Xmax \ T.
Qua các bước phân tích ở trên, bài toán sẽ được giải thông qua các bước sau:
Nhưng vấn đề của bài toán này là khi N lớn (xấp xỉ 1 tỉ) thì NN Có giá trị rất lớn mà không có một kiểu dữ liệu căn bản nào có thể chứa được. Vì vậy ở đây ta sẽ đi tìm một giải pháp khác mà không phải tính toán số cực lớn NN
Dễ thấy A luôn có thể phân tích thành tích lũy thừa các số nguyên tố A = p1x1 p2x2 … pkxk Do đó điều kiện cần để NN chia hết cho A là N chia hết cho tích T =p1p2 … pk (Ta có thể chứng minh điều này đễ dàn bằng phản chứng). Ta đăt N = T * i (i ≤ N) Khi đó NN = (T*i)T*i = TT*i * iT*i (với T = P1P2....Pk)
Ta tìm điều kiện đủ để NN chia hết cho A:
Gọi Xmax = MAX{x1, x2.....xn} khi đó nếu N= T*i ≥ Xmax lúc đó TT*i sẽ chia hết cho A vì vậy NN chia hết cho A. Vì T, Xmax luôn là hằng số với mỗi giá trị nhập vào của A ta sẽ có i ≥ Xmax \ T bài toán trở thành tìm giá trị nhỏ nhất của i thỏa mãn i ≥ Xmax \ T.
Qua các bước phân tích ở trên, bài toán sẽ được giải thông qua các bước sau:
- Phân tích A ra tích lũy thừa nguyên tố dạng A = p1x1 p2x2 … pkxk Tính T = p1p2...pn và Xmax = Max{x1,x2, ...xn}
- Tìm giá trị nhỏ nhất thỏa mãn i ≥ Xmax \ T
- Xuất ra kết quả N = T * i
#include <iostream>
#include <conio.h>
using namespace std;
int PhanTichNguyenTo( int soNhap, int& Xmax);
bool isPrime(int num);
void NhapXuat();
void main()
{
NhapXuat();
}
void NhapXuat()
{
int Xmax = 0;
int A ;
int i;
while((cout << endl<< "Nhap so A = ")&&cin >> A)
{
int temp = PhanTichNguyenTo(A,Xmax);
i = ceil(Xmax/(float)temp);
cout << "So N nho nhat thoa man dieu kien tren la " << temp * i;
}
}
/*Ham tra ve tich cac uoc nguyen to cua so nhap
va so mu lon nhat cua tich nguyen to*/
int PhanTichNguyenTo( int soNhap, int& Xmax)
{
int T=1;
int maxExp = 0;
if(isPrime(soNhap))
{
maxExp =1;
T= soNhap;
}
else
for(int i = 2; i <= sqrt(soNhap); i++)
{
int j = 0;
if(isPrime(i) && (soNhap % i ==0))
{
T *= i;
int temp = soNhap;
int exp =0;
while(temp % i ==0)
{
temp = temp / i;
exp++;
}
if(maxExp < exp) maxExp = exp;
}
}
Xmax = maxExp;
return T;
}
bool isPrime(int num)
{
bool result = true;
if(num == 0|| num == 1)
result = false;
else
{
num = abs(num);
for(int i = 2; i <= sqrt(num); i++)
if(num % i == 0)
result = false;
}
return result;
}
Không có nhận xét nào:
Đăng nhận xét