Một khả năng khác sẽ là một trong những điều sau đây:
Bạn bắt đầu với số thập phân lớn nhất của loại "1111111 ... 1111" được hỗ trợ bởi loại dữ liệu được sử dụng
Thuật toán giả định rằng đầu vào nhỏ hơn số này; nếu không, bạn sẽ phải sử dụng một loại dữ liệu khác.
Ví dụ: Khi sử dụng long long
, bạn bắt đầu với số 1111111111111111111
.
- Sau đó xử lý từng chữ số thập phân từ trái sang phải:
- Cố gắng thay đổi chữ số từ 1 thành 0.
- Nếu kết quả vẫn lớn hơn đầu vào của bạn, hãy thực hiện thay đổi (thay đổi chữ số thành 0).
- Nếu không, chữ số vẫn là 1.
Thí dụ
Input = 10103
Start: 111111
Step 1: [1]11111, try [0]11111; 011111 > 10103 => 011111
Step 2: 0[1]1111, try 0[0]1111; 001111 < 10103 => 011111
Step 3: 01[1]111, try 01[0]111; 010111 > 10103 => 010111
Step 4: 010[1]11, try 010[0]11; 010011 < 10103 => 010111
Step 5: 0101[1]1, try 0101[0]1; 010101 < 10103 => 010111
Step 6: 01011[1], try 01011[0]; 010110 > 10103 => 010110
Result: 010110
Bằng chứng về sự đúng đắn:
Chúng tôi xử lý chữ số bằng chữ số trong thuật toán này. Trong mỗi bước, có những chữ số có giá trị đã được biết và chữ số chưa biết giá trị.
Trong mỗi bước, chúng tôi thăm dò chữ số ngoài cùng bên trái.
Chúng tôi đặt chữ số đó thành "0" và tất cả các chữ số không xác định khác thành "1". Bởi vì chữ số được thăm dò là số có nghĩa nhất trong số các chữ số chưa biết, số kết quả là số lớn nhất có thể có với chữ số đó là "0". Nếu số này nhỏ hơn hoặc bằng đầu vào, chữ số được thăm dò phải là "1".
Mặt khác, số kết quả nhỏ hơn tất cả các số có thể có trong đó chữ số được thăm dò là "1". Nếu số kết quả lớn hơn đầu vào, chữ số phải là "0".
Điều này có nghĩa là chúng ta có thể tính toán một chữ số trong mỗi bước.
Mã C
(Mã C cũng hoạt động theo C ++):
long long input;
long long result;
long long digit;
... read in input ...
result = 1111111111111111111ll;
digit = 1000000000000000000ll;
while( digit > 0 )
{
if(result - digit > input)
{
result -= digit;
}
digit /= 10;
}
... print out output ...