我發現一個很好的數學問題,但我仍然無法解決它,我試圖找到一個解決方案,使用谷歌,發現它可以解決使用二進制索引樹數據結構,但解決方案並不清楚。如何使用BIT解決此問題?
這裏稱爲查找魔術三胞胎的問題,它可以在UVA線上解題系統中找到:
(A + B^2)模k = C^3模k,其中一個< = B < = c和1 < = a,b,c < = n。
給定n和k(1 < = n,k < = 10^5),對於已知的n和k值存在多少個不同的魔術三元組。如果三個值中的任何一個在三個中都不相同,則三元組與另一個不同。
,並在這裏,我找到了解決辦法:
#include <cstdio>
#include <cstring>
using namespace std;
typedef long long int64;
const int MAX_K = (int)(1e5);
int N, K;
struct BinaryIndexedTree{
typedef int64 bit_t;
static const int MAX_BIT = 3*MAX_K + 1;
bit_t data[MAX_BIT+1];
int SIZE;
void init(int size){
memset(data, 0, sizeof(data));
SIZE = size;
}
bit_t sum(int n){
bit_t ret = 0;
for(;n;n-=n&-n){
ret += data[n];
}
return ret;
}
bit_t sum(int from, int to){
return sum(to)-sum(from);
}
void add(int n, bit_t x){
for(n++;n<=SIZE;n+=n&-n){
data[n]+=x;
}
}
};
BinaryIndexedTree bitree;
void init(){
scanf("%d%d", &N, &K);
}
int64 solve(){
bitree.init(2*K+1);
int64 ans = 0;
for(int64 i=N; i>=1; i--){
int64 b = i * i % K, c = i * i * i % K;
bitree.add(c, 1);
bitree.add(c+K, 1);
bitree.add(c+2*K, 1);
int64 len = i;
if(len >= K){
ans += (len/K) * bitree.sum(K);
len %= K;
}
if(len > 0){
ans += bitree.sum(b + 1, b + len + 1);
}
}
return ans;
}
int main(){
int T;
scanf("%d", &T);
for(int i=0; i<T; i++){
init();
printf("Case %d: %lld\n", i+1, solve());
}
return 0;
}
您可以添加一些測試用例,以便可以驗證任何解決方案嗎? –
@MarkusJarderot [鏈接] http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=3860有問題的鏈接,例子是n = 10和k = 7有27個不同的三胞胎。 – user2456277
那麼你想了解這個解決方案,還是不行?它不太清楚你的實際問題是什麼。 –