题目:这里
题意:n个城市,每个城市有个魅力值vi,首先,有n条路将这n个城市连成一个环,1号城市连2号城市,2号连3号****n号连1号城市,每条路的魅力值是其连接的两个城市
的魅力值的乘积,这n个城市其中还有k个是特殊城市,每个特殊城市和任意一条城市都有一条路连接,看题目下面的图,保证每两个城市之间最多只有一条路,问所有路的
魅力值之和是多少?
首先是连接成环的路线魅力值,很好算,然后每个特殊城市的路线,先求出所有城市的魅力值之和sum,依次求特殊城市的时候用sum减去这个特殊城市本身以及两边相邻的城市
魅力值(因为相邻两边的路已经算过了),再乘这个特殊城市本身魅力值就行,注意这样可能会有路算重复了,而题目显然每条路只能算一次,每次再减去已经出现过的特殊城市
的魅力值之和就行了,注意可能之前出现的特殊城市可能会是现在的特殊城市的左右相邻的城市之一,这样的话就不用减了,因为已经减了,标记一下就行。
1 #include<cstdio> 2 #include<cstring> 3 #include<iostream> 4 #include<algorithm> 5 using namespace std; 6 7 typedef long long ll; 8 const int M = 1e5 + 10; 9 ll a[M];bool has[M]; 10 11 int main() 12 { 13 int n,m; 14 ll sum=0,ans=0; 15 scanf("%d%d",&n,&m); 16 for (int i=1 ; i<=n ; i++) 17 { 18 scanf("%I64d",&a[i]); 19 if (i>1) ans+=(a[i]*a[i-1]); 20 sum+=a[i]; 21 } 22 ans+=a[1]*a[n]; 23 memset(has,false,sizeof(has)); 24 ll cas=0; 25 while (m--) 26 { 27 int x,l,r; 28 scanf("%d",&x); 29 has[x]=true; 30 if (x-1==0) l=n; 31 else l=x-1; 32 if (x+1==n+1) r=1; 33 else r=x+1; 34 ans+=(sum-a[x]-a[l]-a[r])*a[x]; 35 ll we=cas; 36 if (has[l]) we-=a[l]; 37 if (has[r]) we-=a[r]; 38 ans-=we*a[x]; 39 cas+=a[x]; 40 } 41 printf("%I64d\n",ans); 42 return 0; 43 }