题目
题意:
给定n个数,输出有多少个点对满足a[i]*a[j]=任意数的k次方(i<j)。
分析:
将每个数分解为质因数,两个数相乘满足条件那么显然他们的质因数也满足条件。所以我们对一个数进行质因子分解,形成一个vector数组,数组里每个元素存对应的质因数及其指数,指数应对k取模,与其匹配的数组就是对应的指数为k-指数。用map存放这个vector,就可以log(n)找出。
#include <iostream>
#include <vector>
#include <map>
using namespace std;
typedef long long ll;
vector<pair<int,int> > temp;
map<vector<pair<int,int> >,int> ma;
void divide(int n,int k)
{
int a = n;
for (int i = 2; i * i <= n; i++)
{
if( a % i == 0 )
{
int num = 0;
while( a % i == 0 )
{
a /= i;
num ++;
}
num %= k;
if( num != 0 ) temp.push_back(make_pair(i,num));
}
}
if( a > 1 ) temp.push_back(make_pair(a,1));
}
int main()
{
ios::sync_with_stdio(false);
cin.tie(0);
int n,k;
cin >> n >> k;
ll ans = 0;
for (int i = 1; i <= n; i++)
{
int x;
cin >> x;
temp.clear();
divide(x,k);
vector<pair<int,int> > aim;
for (int i = 0; i < temp.size(); i++)
{
aim.push_back(make_pair(temp[i].first,k-temp[i].second));
}
ans += ma[aim];
ma[temp]++;
}
cout << ans << '\n';
return 0;
}