题意
分
解
n
∗
m
,
使
得
满
足
两
个
条
件
:
(
1
)
分
解
的
数
中
可
以
组
合
成
n
组
,
每
组
的
值
为
m
(
2
)
分
解
的
数
中
可
以
组
合
成
m
组
,
每
组
的
值
为
n
分解n*m,使得满足两个条件:\\(1)分解的数中可以组合成n组,每组的值为m\\(2)分解的数中可以组合成m组,每组的值为n
分解n∗m,使得满足两个条件:(1)分解的数中可以组合成n组,每组的值为m(2)分解的数中可以组合成m组,每组的值为n
要
使
得
分
解
的
个
数
少
,
若
相
同
输
出
字
典
序
最
大
的
一
种
方
案
要使得分解的个数少,若相同输出字典序最大的一种方案
要使得分解的个数少,若相同输出字典序最大的一种方案
思路
考
虑
n
=
=
m
情
况
简
单
直
接
输
出
n
个
n
即
可
,
显
然
考虑n==m情况\\简单直接输出n个n即可,显然
考虑n==m情况简单直接输出n个n即可,显然
考
虑
n
!
=
m
情
况
,
方
便
起
见
,
直
接
令
n
<
m
思
考
:
(
1
)
m
、
m
、
m
、
.
.
.
、
m
,
共
n
个
考虑n!=m情况,方便起见,直接令n<m\\思考:\\(1)m、m、m、...、m,共n个
考虑n!=m情况,方便起见,直接令n<m思考:(1)m、m、m、...、m,共n个
(
2
)
n
、
n
、
n
、
.
.
.
.
、
n
,
共
n
个
(2)n、n、n、....、n,共n个
(2)n、n、n、....、n,共n个
把
(
1
)
中
的
每
个
m
都
减
掉
n
可
得
到
m
−
n
共
n
个
把(1)中的每个m都减掉n可得到m-n共n个
把(1)中的每个m都减掉n可得到m−n共n个
(
3
)
m
−
n
、
m
−
n
、
m
−
n
、
.
.
.
、
m
−
n
,
共
n
个
(3)m-n、m-n、m-n、...、m-n,共n个
(3)m−n、m−n、m−n、...、m−n,共n个
观
察
(
1
)
(
2
)
与
(
2
)
(
3
)
很
相
似
,
产
生
联
想
,
这
会
不
会
是
动
态
规
划
,
由
一
个
状
态
转
移
另
外
一
个
状
态
呢
?
观察(1)(2)与(2)(3)很相似,产生联想,这会不会是动态规划,\\由一个状态转移另外一个状态呢?
观察(1)(2)与(2)(3)很相似,产生联想,这会不会是动态规划,由一个状态转移另外一个状态呢?
证明
设
d
p
(
n
,
m
)
表
示
分
解
n
∗
m
的
方
案
(
注
意
n
<
m
)
设dp(n, m)表示分解n*m的方案(注意n<m)
设dp(n,m)表示分解n∗m的方案(注意n<m)
d
p
(
n
,
,
m
)
与
d
p
(
m
−
n
,
n
)
关
系
呢
?
dp(n,,m)与dp(m - n, n)关系呢?
dp(n,,m)与dp(m−n,n)关系呢?
d
p
(
n
,
m
)
:
存
在
n
组
m
以
及
m
组
n
d
p
(
m
−
n
,
n
)
:
存
在
m
−
n
组
n
以
及
n
组
m
−
n
dp(n, m):存在n组m以及m组n\\dp(m-n, n):存在m-n组n以及n组m-n
dp(n,m):存在n组m以及m组ndp(m−n,n):存在m−n组n以及n组m−n
d
p
(
n
,
m
)
=
d
p
(
m
−
n
,
n
)
+
n
个
n
dp(n, m) = dp(m -n, n)+n个n
dp(n,m)=dp(m−n,n)+n个n
很显然
m − n 组 n + n 组 n = m 组 n m-n组n+n组n=m组n m−n组n+n组n=m组n
n 组 m − n + n 组 n = n 组 m n组m-n+n组n=n组m n组m−n+n组n=n组m
因
为
d
p
(
m
−
n
,
n
)
是
最
优
状
态
,
+
n
个
n
显
然
是
最
优
秀
的
转
移
因为dp(m-n,n)是最优状态,+n个n显然是最优秀的转移
因为dp(m−n,n)是最优状态,+n个n显然是最优秀的转移
d
p
(
)
初
始
状
态
很
简
单
,
即
d
p
(
c
,
c
)
为
c
个
c
dp()初始状态很简单,即dp(c,c)为c个c
dp()初始状态很简单,即dp(c,c)为c个c
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const int maxn = 1e4 + 10;
int n, m;
vector<int> v;
void dfs(int n, int m){
if(n == 0) return ;
for(int i = 1; i <= n; i++){
v.push_back(n);
}
int res = m - n;
if(res > n) swap(res, n);
dfs(res, n);
}
int main(){
int t;
scanf("%d", &t);
while(t--){
v.clear();
scanf("%d%d", &n, &m);
if(n > m) swap(n, m); ///n < m
dfs(n, m);
ll siz = v.size();
printf("%lld\n", siz);
for(ll i = 0; i < siz; i++){
printf("%d%c", v[i], i == siz - 1 ? '\n' : ' ');
}
}
return 0;
}