CF1527 C-水题

该博客介绍了一道编程题目,要求计算给定序列的所有子序列中相同数对的数量之和。题目中提到,子序列可以通过删除序列两端的元素获得。博主提供了一个解决方案,利用哈希映射存储每个数的前缀和,从而快速计算每个数对的贡献。最后,博主给出了C++代码实现,并在多个测试用例上进行了验证。
摘要由CSDN通过智能技术生成

题目
The weight of a sequence is defined as the number of unordered pairs of indexes (i,j) (here i<j) with same value (ai=aj). For example, the weight of sequence a=[1,1,2,2,1] is 4. The set of unordered pairs of indexes with same value are (1,2), (1,5), (2,5), and (3,4).

You are given a sequence a of n integers. Print the sum of the weight of all subsegments of a.

A sequence b is a subsegment of a sequence a if b can be obtained from a by deletion of several (possibly, zero or all) elements from the beginning and several (possibly, zero or all) elements from the end.

Input
Each test contains multiple test cases. The first line contains the number of test cases t (1≤t≤105). Description of the test cases follows.

The first line of each test case contains a single integer n (1≤n≤105).

The second line of each test case contains n integers a1,a2,…,an (1≤ai≤109).

It is guaranteed that the sum of n over all test cases does not exceed 105.

Output
For each test case, print a single integer — the sum of the weight of all subsegments of a.

题意:
一道水题
求所有子序列中的相同数对的数量之和
早上补的时候还是大佬(佐爷)给我讲的
看来群里只有我是fw

题解:
假设两个相同数位置分别为 i,j(i<j)
则它们在所有子序列中的贡献为i*(n-j+1)
由此,每个j匹配前面所有 i (即 i 的前缀和 i1+i2+i3+…)
即可,然后用map<int,int>存某个数的前缀和即可

#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<queue>
#include<map>
#define me(x,y) memset(x,y,sizeof(x))
#define rep(i,a,b) for(ll i=a;i<=b;i++)
#define rev(i,a,b) for(ll i=b;i>=a;i--)
using namespace std;
typedef long long ll;
typedef pair<ll, ll> P;
const ll N = 2e5 + 7, mod = 1e12 + 7;
ll n, t, k  ,ans;
map<ll, ll>mp;
int main() {
	cin >> t;
	while (t--) {
		ans = 0;
		cin >> n;
		rep(i, 1, n) {
			cin >> k;
			if (!mp.count(k)) mp[k] = i;
			else {
				ans += mp[k] * (n - i + 1);
				mp[k] += i;
			}
		}
		cout << ans << "\n";
		mp.clear();
	}
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值