细胞分裂
作者:互联网
Hanks 博士是 BT (Bio-Tech,生物技术) 领域的知名专家。
现在,他正在为一个细胞实验做准备工作:培养细胞样本。
Hanks 博士手里现在有 N 种细胞,编号从 1~N,一个第 i 种细胞经过 1 秒钟可以分裂为SiSi个同种细胞(SiSi为正整数)。
现在他需要选取某种细胞的一个放进培养皿,让其自由分裂,进行培养。
一段时间以后,再把培养皿中的所有细胞平均分入 M 个试管,形成 M 份样本,用于实验。
Hanks 博士的试管数 M 很大,普通的计算机的基本数据类型无法存储这样大的 M 值,但万幸的是,M 总可以表示为 m1m1 的 m2m2 次方,即 M=mm21M=m1m2,其中 m1,m2m1,m2 均为基本数据类型可以存储的正整数。
注意,整个实验过程中不允许分割单个细胞,比如某个时刻若培养皿中有 4 个细胞,Hanks 博士可以把它们分入 2 个试管,每试管内 2 个,然后开始实验。
但如果培养皿中有 5个细胞,博士就无法将它们均分入 2 个试管。
此时,博士就只能等待一段时间,让细胞们继续分裂,使得其个数可以均分,或是干脆改换另一种细胞培养。
为了能让实验尽早开始,Hanks 博士在选定一种细胞开始培养后,总是在得到的细胞“刚好可以平均分入 M 个试管”时停止细胞培养并开始实验。
现在博士希望知道,选择哪种细胞培养,可以使得实验的开始时间最早。
输入格式
输入文件共有三行。
第一行有一个正整数N,代表细胞种数。
第二行有两个正整数m1,m2m1,m2,以一个空格隔开,mm21m1m2即表示试管的总数M。
第三行有N个正整数,第i个数SiSi表示第i种细胞经过1秒钟可以分裂成同种细胞的个数。
输出格式
输出文件共一行,为一个整数,表示从开始培养细胞到实验能够开始所经过的最少时间(单位为秒)。
如果无论Hanks博士选择哪种细胞都不能满足要求,则输出整数-1。
数据范围
1≤N≤100001≤N≤10000,
1≤m1≤300001≤m1≤30000,
1≤m2≤100001≤m2≤10000,
1≤Si≤2∗1091≤Si≤2∗109
输入样例:
2
24 1
30 12
输出样例:
2
思路:对m1进行质因数分解,计算出每个s的所需的最大分裂次数,然后再所有s所求得的结果中取个最小值
#include <iostream> #include <cstring> #include <algorithm> using namespace std ; const int N = 3000,M = 10010 ; int primes[N],e[N],cnt ; int n,m1,m2 ; int main(){ cin >> n >> m1 >> m2 ; for(int i=2;i<=m1/i;i++){ if(m1%i == 0){ int s = 0 ; while(m1 % i == 0){ s ++ ; m1 /= i ; } primes[cnt] = i ; e[cnt] = s ; cnt ++ ; } } if(m1>1){ primes[cnt] = m1 ; e[cnt] = 1 ; cnt ++ ; } for(int i=0;i<cnt;i++){ e[i] *= m2 ; } int res = 0x3f3f3f3f ; for(int i=0;i<n;i++){ int num ,t = 0,tmp = 0 ; cin >> num ; bool flag = true ; for(int j=0;j<cnt;j++){ if(num%primes[j]){ flag = false ; break ; }else{ int p = primes[j] ; while(num%p==0){ tmp ++ ; num /= p ; } if(tmp<e[j]){ if(e[j]%tmp == 0){ t = max(t,e[j]/tmp) ; }else{ t = max(t,e[j]/tmp+1) ; } } } } if(!flag) continue ; res = min(res,t) ; } if(res == 0x3f3f3f3f){ res = -1 ; } cout << res << endl ; return 0 ; }
...
标签:细胞分裂,int,细胞,m1,m2,Hanks,试管 来源: https://www.cnblogs.com/gulangyuzzz/p/12381615.html