A-Tetrahedron (mathematics expectation, linear inverse element) in the 5th field of Hangzhou Electric Power

Topic portal

Meaning of the question: give you a right-angled tetrahedron. The length of the three edges of this right-angled tetrahedron is a random integer in [1,n]. Let's set the height of the bottom surface of this right-angled tetrahedron to h, and find the mathematics of 1/h² What are the expectations.

Idea: After a series of calculations, we get 1/h²=1/a² + 1/b² + 1/c². Because a, b, and c are random numbers generated with a moderate probability of [1, n], we only need to calculate the expectation of 1/a² and multiply it by 3. The expectation of 1/a² = (1/1² * 1/n + 1/2² * 1/n + 1/3² * 1/n + …+ 1/n² * 1/n), 1/n can be put forward, So it is the sum of the reciprocals of the squares of the first n numbers. Preprocessing is equivalent to the reciprocal prefix sum. There is an optimization here, that is, when using the inverse element, you do not need to find the time of logn every time, you can directly find the inverse element linearly, and just use it directly.

Code:

#include<bits/stdc++.h>
#pragma GCC optimize("Ofast")
#define endl '\n'
#define null NULL
#define ls p<<1
#define rs p<<1|1
#define fi first
#define se second
#define mp make_pair
#define pb push_back
#define ll long long
//#define int long long
#define pii pair<int,int>
#define pdd pair<double,double>
#define ull unsigned long long
#define unmap unordered_map
#define all(x) x.begin(),x.end()
#define IOS ios::sync_with_stdio(false);cin.tie(0);cout.tie(0);
#define ct cerr<<"Time elapsed:"<<1.0*clock()/CLOCKS_PER_SEC<<"s.\n";
char *fs,*ft,buf[1<<20];
#define gc() (fs==ft&&(ft=(fs=buf)+fread(buf,1,1<<20,stdin),fs==ft))?0:*fs++;
inline int read(){
    
    int x=0,f=1;char ch=gc();
while(ch<'0'||ch>'9'){
    
    if(ch=='-')f=-1;ch=gc();}
while(ch>='0'&&ch<='9'){
    
    x=x*10+ch-'0';ch=gc();}
return x*f;}
using namespace std;
const int N=6e6+5;
const int inf=0x3f3f3f3f;
const int mod=998244353;
const double eps=1e-6;
const double PI=acos(-1);
ll j[N],inv[N];
ll qpow(ll a,ll b)
{
    
    
    ll res=1;
    while(b)
    {
    
    
        if(b&1)
            res=res*a%mod;
        a=a*a%mod;
        b>>=1;
    }
    return res;
}
void init()
{
    
    
    j[1]=1;
    inv[1]=1;
    for(int i=2;i<N;++i)
        inv[i]=(ll)(mod-mod/i)*inv[mod%i]%mod;
    for(int i=2;i<N;++i)
        j[i]=(j[i-1]+inv[i]*inv[i]%mod)%mod;
}
signed main()
{
    
    
    int T;scanf("%d",&T);
    init();
    while(T--)
    {
    
    
        int n;scanf("%d",&n);
        ll res=(j[n]*inv[n]*3%mod);
        printf("%lld\n",res);
    }
}

Guess you like

Origin blog.csdn.net/Joker_He/article/details/107824961