Đây là bài viết thứ hai trong series bài viết về Công thức Toán học và Tính chất số học đặc biệt trong Lập trình thi đấu. Để xem lại bài viết trước, các bạn có thể nhấn vào đây.
V. Một số đẳng thức đáng lưu ý
Qua quá trình nghiên cứu và đúc kết từ các kỳ thi HSG Tin học các cấp và kinh nghiệm cá nhân, tác giả nhận thấy các dãy số với công thức có sẵn thường được áp dụng rất nhiều trong các bài toán về chủ đề Số học trong Tin học. Tất nhiên, không ai cho các bạn một dãy số rồi bắt tìm công thức của nó cả, nhưng những dãy số sẽ được lồng ghép vào các bài toán lớn để gây khó khăn cho người giải ở những bước tìm kết quả cuối cùng. Vì vậy, tôi đã tổng hợp những dãy số rất hữu ích có thể sử dụng trong lập trình thi đấu, hy vọng nó đủ dùng. Các dãy số chủ yếu sẽ có được công thức từ việc chứng minh quy nạp hoặc biến đổi theo phương pháp của THCS, bạn đọc cố gắng đọc kĩ để hiểu được thì sẽ nhớ rất lâu!
1.
Chứng minh: Sử dụng quy nạp toán học:
- Với ta thấy đẳng thức đúng.
- Giả sử đẳng thức đúng với tức là
- Chứng minh đẳng thức đúng với : . (Do giả thiết quy nạp). . . . (điều phải chứng minh).
Vậy đẳng thức đúng với mọi .
2.
Chứng minh:
- Với ta có đẳng thức đúng.
- Giả sử đẳng thức đúng với tức là .
- Chứng minh đẳng thức đúng với : . . . Giờ ta cần chứng minh: . Thật vậy, ta có: đẳng thức đúng.
Vậy đẳng thức (1) đúng với đồng nghĩa với việc đẳng thức ban đầu đúng với .
3.
Chứng minh:
- Với ta có đẳng thức đúng.
- Giả sử đẳng thức đúng với tức là .
- Chứng minh đẳng thức đúng với : . Thật vậy, ta có: (Do giả thiết quy nạp). . .
Vậy ta có điều phải chứng minh, đẳng thức đúng với .
4.
Chứng minh:
- Với ta có đẳng thức đúng.
- Giả sử đẳng thức đúng với tức là .
- Chứng minh đẳng thức đúng với : . Thật vậy, ta có: . (Do giả thiết quy nạp).
Vậy ta có điều phải chứng minh, đẳng thức đúng với .
VI. Bất đẳng thức
Các bất đẳng thức được ứng dụng nhiều nhất trong Toán học cũng như Tin học ở mức độ thi HSG sẽ là bất đẳng thức AM - GM và bất đẳng thức Bunyakovsky. Trong các bài toán số học, hai bất đẳng thức này sẽ có tác dụng rất lớn trong việc đặt cận cho bài toán, từ đó dễ dàng thực hiện các công việc liên quan tới đếm số lượng. Quá trình chứng minh của các bất đẳng thức này là thành quả toán học lâu dài và cũng không cần thiết cho bạn đọc nên người viết xin phép không trình bày ở đây.
1. Bất đẳng thức AM - GM
Các bạn thường được biết đến bất đẳng thức này trong chương trình Toán trung học là bất đẳng thức Cauchy. Nhưng thực ra nó chỉ được chứng minh bởi Cauchy mà thôi, còn tên quốc tế của nó phải là Bất đẳng thức AM - GM, hay Bất đẳng thức trung bình cộng - trung bình nhân. Bất đẳng thức này được phát biểu như sau: "Trung bình cộng của số luôn luôn lớn hơn hoặc bằng trung bình nhân của chúng. Dấu bằng xảy ra khi và chỉ khi cả số đó bằng nhau":
Dấu xảy ra
Bất đẳng thức này cũng hoàn toàn đúng trong trường hợp hai giá trị trung bình có hệ số: Với số và các hệ số nếu đặt thì:
Dấu xảy ra
2. Bất đẳng thức Bunyakovsky
Là dạng cơ bản của bất đẳng thức Cauchy - Schwarz, một bất đẳng thức được áp dụng trong nhiều lĩnh vực của Toán học. Dưới đây là dạng tổng quát của bất đẳng thức Bunyakovsky cho hai bộ số và :
Dấu xảy ra . Quy ước nếu thì
VI. Bài tập áp dụng
1. Tổng liên tiếp
Đề bài
Sau khi học về số học, Minh đã biết cách tính tổng của số tự nhiên liên tiếp. Minh làm thêm nhiều bài tập số học và băn khoăn, liệu với số tự nhiên thì có thể phân tích được thành tổng các số tự nhiên liên tiếp hay không? Ví dụ với thì có thể phân tích theo cách: .
Yêu cầu: Hãy viết chương trình giúp Minh đếm số cách phân tích số tự nhiên thành tổng cách số tự nhiên liên tiếp?
Input:
- Gồm một dòng duy nhất chứa số tự nhiên .
Ràng buộc:
- .
Output:
- Chứa một số nguyên duy nhất là số lượng cách phân tích số tự nhiên thành tổng các số tự nhiên liên tiếp.
Sample Input:
9
Sample Output:
3
Ý tưởng
Giả sử phân tích được thành một dãy liên tiếp:
Giờ ta đánh giá cận trên và cận dưới của :
- Chắc chắn cận dưới của là 0.
- Giả sử tức là phân tích thành một dãy số liên tiếp bắt đầu từ (nghĩa là sẽ đạt giá trị lớn nhất). Khi đó tức là . Tới đây ta có thể duyệt tất cả các giá trị thỏa mãn rồi tìm ra bằng công thức . Nếu là số nguyên thì ta có một cách phân tích.
Độ phức tạp: .
Code mẫu
#pragma GCC optimize("O3","unroll-loops")
#pragma GCC target("avx2")
#include <bits/stdc++.h>
#define int long long
using namespace std;
void solution(int n)
{
int res = 0;
for (int l = 0; (l + 1) * (l + 2) <= 2 * n; ++l)
{
double a = (double) n / (l + 1) - (double) l / 2;
res += (a == (int) a);
}
cout << res;
}
main()
{
ios_base::sync_with_stdio(false);
cin.tie(nullptr);
int n;
cin >> n;
solution(n);
return 0;
}
2. Thi đấu bóng đá
Đề bài
Đất nước CP tổ chức một giải đấu bóng đá quốc nội. Có đội bóng tham gia thi đấu, mỗi đội đều đấu với tất cả các đội còn lại. Quốc vương của đất nước CP là một người rất yêu thích toán học, lần này, ông đặt ra một câu hỏi cho vị tể tướng đáng kính của mình như sau: Giả sử đội thứ giành chiến thắng trong trận đấu, thì tổng của mọi giá trị với là bao nhiêu?
Tể tướng cảm thấy câu hỏi này rất khó, vì có quá nhiều trường hợp có thể xảy ra. Vì vậy, ông ấy xin phép trả lời nhà vua bằng cách đưa ra giá trị lớn nhất và giá trị nhỏ nhất có thể của tổng và đã được nhà vua chấp thuận. Tuy nhiên, việc này vẫn không phải là một vấn đề đơn giản.
Yêu cầu: Biết trước giá trị là số lượng đội tham gia giải đấu, hãy giúp tể tướng tìm ra giá trị nhỏ nhất và giá trị lớn nhất của tổng
Input:
- Dòng đầu tiên chứa số nguyên dương – số lượng testcases.
- dòng tiếp theo, mỗi dòng chứa một số nguyên dương .
Ràng buộc:
- .
- .
Output:
- Trên dòng, mỗi dòng đưa ra một số nguyên duy nhất là kết quả của testcase tương ứng. Chỉ cần đưa ra phần dư của kết quả sau khi chia cho .
Sample Input:
2
3
5
Sample Output:
3 5
20 30
Ý tưởng
Nhận xét: .
Bài toán trở thành: Tìm min và max của khi đã biết đẳng thức . Ta có:
-
. Bất đẳng thức này là hệ quả trực tiếp của bất đẳng thức Cauchy Schwarz, hay còn gọi là bất đẳng thức Bunyakovsky với hai bộ số và . Vậy .
-
Đối với tìm max, ta nhận xét thấy biểu thức đạt giá trị max, thì tạo ra một dãy số liên tục, tức là đội thứ nhất thắng trận, đội thứ thắng trận,..., đội thứ thắng trận (đội thắng toàn bộ đội trước đó). Vậy max là .
Ta cần lưu ý sử dụng nghịch đảo module đối với ngôn ngữ C++ để tránh bị tràn số.
Độ phức tạp: .
Code mẫu
#pragma GCC optimize("O3","unroll-loops")
#pragma GCC target("avx2")
#include <bits/stdc++.h>
#define int long long
using namespace std;
const int mod = 1e9 + 7;
int modular_exponentiation(int a, int b, int m)
{
if (b == 0)
return 1;
int half = modular_exponentiation(a, b / 2LL, m) % m;
if (b & 1)
return (((half * half) % m) * (a % m)) % m;
else
return (half * half) % m;
}
int inverse_modulo(int a, int m)
{
return modular_exponentiation(a, m - 2, m);
}
void solution(int n, int m)
{
int min_value = ((n % m) * modular_exponentiation(n - 1, 2, m)) % m;
int max_value = ((((n % m) * ((n - 1) % m)) % m) * ((2 * n - 1) % m)) % m;
min_value = (min_value * inverse_modulo(4, m)) % m;
max_value = (max_value * inverse_modulo(6, m)) % m;
cout << min_value << ' ' << max_value << endl;
}
main()
{
ios_base::sync_with_stdio(false);
cin.tie(0); cout.tie(0);
int ntest;
cin >> ntest;
while (ntest--)
{
int n;
cin >> n;
solution(n, mod);
}
return 0;
}
VIII. Lời kết
Như vậy, chúng ta đã cùng nhau tìm hiểu những công thức, định lý rất thú vị và hữu ích trong Toán học có thể ứng dụng trong Tin học. Tuy nhiên, đó không phải là tất cả. Toán học là một chủ đề cực kỳ rộng lớn và chắc chắn không thể tóm gọn trong vài trang giấy. Vì vậy, trên đây chỉ là một phần rất nhỏ những thứ có thể giúp ích cho các bạn học sinh trong quá trình rèn luyện Thuật toán mà thôi.
Những bài tập của công thức Toán học rất phong phú, phần nhiều sẽ xuất phát từ những công thức rất đơn giản, chỉ cần biến đổi một chút là thu được kết quả. Vì vậy, trước khi suy nghĩ đến những công thức quá phức tạp, bạn đọc hãy tìm cách tạo ra công thức Toán học thông qua những biến đổi thông thường như giải phương trình, chuyển vế đổi dấu hay nhân phá ngoặc,...rất có thể sẽ giúp các bạn tìm ra đáp án bài toán nhanh chóng.
Cuối cùng, hãy chịu khó rèn luyện thật nhiều các bài toán số học để tăng cường khả năng tư duy và mở rộng tầm hiểu biết của bản thân về các công thức toán học. Nơi luyện tập phù hợp nhất chính là thông qua các kỳ thi trên các trang web online judge như codeforces.com hay hackkerank.com,...
IX. Tài liệu tham khảo
- https://codeforces.com/blog/entry/55912
- https://toanhoc247.com/ly-thuyet-va-bai-tap-ve-phuong-phap-quy-nap-toan-hoc-a10798.html
- https://codeforces.com/blog/entry/51272
- https://vnoi.info/wiki/translate/he/Number-Theory-4.md
- https://www.geeksforgeeks.org/eulers-totient-function/
- https://www.geeksforgeeks.org/legendres-formula-highest-power-of-prime-number-that-divides-n/
- https://www.geeksforgeeks.org/largest-power-k-n-factorial-k-may-not-prime/
- https://vi.wikipedia.org/wiki/Bất_đẳng_thức_Cauchy–Schwarz