#include<iostream>
#include<vector>
#include<algorithm>
#include<math.h>
#include<string>
#include<string.h>
#include<iomanip>
#include<map>
#include<queue>
using namespace std;
typedef long long ll;
/*数位dp*/
const int N = 15;
ll dp[N][N];
int num[N], now;
ll dfs(int pos, int sum, bool lead, bool limit)
//pos:第pos位,sum:前面有sum个now,lead:有(true)没有前导零,limit:是(true)不是最高位
{
ll ans = 0;
if (pos == 0)return sum;//0位数
if (!lead and !limit and dp[pos][sum] != -1)return dp[pos][sum];//如果已经记忆了,那就直接返回
int up = (limit ? num[pos] : 9);//limit:数位限制
for (int i = 0; i <= up; i++)
{
//i在pos的数位上从0~up
if (i == 0 and lead)ans += dfs(pos - 1, sum, true, limit and i == up);
//计算000~099
else if (i == now)ans += dfs(pos - 1, sum + 1, false, limit and i == up);
//计算200~299
else if (i != now)ans += dfs(pos - 1, sum, false, limit and i == up);
//计算100~199
}
if (!lead and !limit)dp[pos][sum] = ans;
return ans;
}
ll solve(ll x)
{
int len = 0;
while (x)
{
num[++len] = x % 10;
x /= 10;
}
memset(dp, -1, sizeof(dp));
return dfs(len, 0, true, true);
}
int main()
{
ll a; ll b;
cin >> a>>b;
for (int i = 0; i < 10; i++)now = i, cout << solve(b)-solve(a-1)<<' ';
return 0;
}```