import java.util.*;
public class Main{
public static void main(String[] args){
Scanner in=new Scanner(System.in);
int n=in.nextInt(),copy=n;
// 取每一位上的数放入数组
List<Integer> list=new ArrayList<>();
while(n!=0){
int res=n%10;
list.add(0,res);
n/=10;
}
// 转数组
n=list.size();
int[] arr=new int[n];
for(int i=0;i<n;i++){
arr[i]=list.get(i);
}
// 处理:ans表示多加了的数的和
int index=n-1,ans=0;
while(true){
int cur=arr[index];
if(cur>4){
// //1.判断前面高位中是否有数字4
int i=index-1;
while(i>=0&&arr[i]!=4){
i--;
}
if(i>=0){//在i处是4,多加的数是10的x次方
int base=1;
for(int j=i;j<index;j++){
base*=10;
}
ans+=base;
//i处的位值减1:表示第i个位次处理了一次,将位值减1,下同
arr[i]--;
}else{// 2.前面高位中没有4,多加的数为1
ans++;
//上一个非0更高位减1:如59变49
i=index-1;
while(i>=0&&arr[i]==0){
i--;
}
//找不到,说明处理结束,下同
if(i<0)break;
arr[i]--;
//从i到index的路程中的0位全部置为9:模仿借位
for(int j=i+1;j<index;j++){
arr[j]=9;
}
}
}else{
//向最近一个高位借位(该位必须不为0)
int i=index-1;
while(i>=0&&arr[i]==0){
i--;
}
if(i<0)break;
arr[i]--;
// 中间的数全部置9(包括index)
for(int j=i+1;j<=index;j++){
arr[j]=9;
}
}
}
System.out.println(copy-ans);
}
}
简要:每个数位从9到0均统计一遍,其中个位上只需统计1次。原数肯定不包含4,但在逐一借位时可能产生4,要单独处理.
如n=99
99: 多加了1, 高位降1,变为89,再判断
89: 多加了1, 高位降1,变为79
79: 多加了1, 高位降1,变为69
……
49: 从40-50都会被跳过,多加了10.
……
09:多加了1,高位无法再降,结束。
对于n=100,个位为0,显然没有跳过4,需要将其降到个位大于4的最大数:99,即借位。
当个位上的数小于4时,需要“借位”,即让上一个非0高位减1,个位的值变9.其实借位后个位值不一定取9,只要比4大就行,不影响结果,为了方便取成9。如105:可以变95或99