传送门:cf 490D
有两个矩形,现在可以对矩形作两种操作。
(1)将矩形去掉一半(某一边变为原来的一半,要求该边可以被2整除)
(2)将矩形去掉三分之一(某一边变为原来的三分之二,要求该边能被3整除)
问最少进行多少次操作可以使得两个矩形的面积相同,并分别输出操作之后的两个矩形的边长
可以发现,两种操作等价于去掉一个素因子2,或者把一个素因子3变成一个素因子2,对其他的素因子不会产生影响,因此首先把剔除2,3的素因子,判断剩余的素因子集合的乘积是否相等,若不相等则无法通过操作使得乘积相等。
然后使得记录使得素因子3和2相等
/******************************************************
* File Name: d.cpp
* Author: kojimai
* Create Time: 2014年11月23日 星期日 18时23分21秒
******************************************************/
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<iostream>
using namespace std;
int cnt2[5];
int cnt3[5];
int main()
{
long long x1,y1,x2,y2;
cin>>x1>>x2;
cin>>y1>>y2;
long long t1 = x1,t2 = x2,k1 = y1,k2 = y2;
memset(cnt2,0,sizeof(cnt2));
memset(cnt3,0,sizeof(cnt3));
while(t1 % 2==0)
{
t1 /= 2;
cnt2[0]++;
}
while(t1 % 3==0)
{
t1 /= 3;
cnt3[0]++;
}
while(t2 % 2==0)
{
t2 /= 2;
cnt2[1]++;
}
while(t2 % 3==0)
{
t2 /= 3;
cnt3[1]++;
}
while(k1 % 2==0)
{
k1 /= 2;
cnt2[2]++;
}
while(k1 % 3==0)
{
k1 /= 3;
cnt3[2]++;
}
while(k2 % 2==0)
{
k2 /= 2;
cnt2[3]++;
}
while(k2 % 3==0)
{
k2 /= 3;
cnt3[3]++;
}
//分别记录下四条边中素因子2,3的个数
if(t1 * t2 != k1 * k2)//剩余的素因子的乘积不等
cout<<-1<<endl;
else
{
int ans = 0;
int x3 = cnt3[0] + cnt3[1];//第一个矩形中2的个数
int y3 = cnt3[2] + cnt3[3];//第一个矩形中3的个数
int x4 = cnt2[0] + cnt2[1];//第二个矩形中2的个数
int y4 = cnt2[2] + cnt2[3];//第二个矩形中3的个数
int xd3 = 0,yd3 = 0,xd4 = 0,yd4 = 0;
if(x3 > y3)
{
xd3 = x3 - y3;
x4 += xd3;//每去掉一个素因子3就对应需要增加一个素因子2
ans += xd3;
}
else if(x3 < y3)
{
yd3 = y3 - x3;
y4 += yd3;
ans += yd3;
}
//对素因子3操作使得3的个数相等
if(x4 > y4)
{
xd4 = x4 - y4;
ans += xd4;
}
else if(x4 < y4)
{
yd4 = y4 - x4;
ans += yd4;
}
//对素因子2操作使得2的个数相等
printf("%d\n",ans);
if(xd3)//需要对第一个矩形进行去三分之一的操作
{
while(x1 % 3 == 0 && xd3)
{
x1 = x1 / 3 * 2;
xd3--;
}
while(x2 % 3 == 0 && xd3)
{
x2 = x2 /3 * 2;
xd3--;
}
}
if(xd4)//需要对第一个矩形进行去二分之一的操作
{
while(x1 % 2 == 0 && xd4)
{
x1 = x1 / 2;
xd4--;
}
while(x2 % 2 == 0 && xd4)
{
x2 /= 2;
xd4--;
}
}
if(yd3)//需要对第二个矩形进行去三分之一的操作
{
while(y1 % 3 == 0 && yd3)
{
y1 = y1/3*2;
yd3--;
}
while(y2 % 3 == 0 && yd3)
{
y2 = y2/3*2;
yd3--;
}
}
if(yd4)//需要对第二个矩形进行去二分之一的操作
{
while(y1 % 2 == 0 && yd4)
{
y1 = y1 / 2;
yd4--;
}
while(y2 % 2 == 0 && yd4)
{
y2 /= 2;
yd4--;
}
}
cout<<x1<<' '<<x2<<endl;
cout<<y1<<' '<<y2<<endl;
}
return 0;
}
需要的操作数,并对应修改边的长度即可