ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

J Counting Triangles(牛客想训练赛3-J题)

2021-07-25 20:02:41  阅读:267  来源: 互联网

标签:int ++ 牛客 edge 训练赛 n0 三角形 Counting z1


题目:https://ac.nowcoder.com/acm/contest/11254/J

题意:给你一张图,n个点,任何两个点之间都有边,边权要么是0要么是1,问三条边权相等的三角形的数量。

题解:图的大小给的是8000,暴力三重循环肯定不行。假设这个三角形中有一个点是重要点,那么咱枚举每一个点当三角形中的重要点;首先,任何三个点都能构成三角形(因为任何两个点之间都有边),所有的三角形只有两种情况,三条边都相等,三条边中有一条边和其他两条边不同,可以看出,这两种三角形有一个共同点,都有两条边是相等的(这两条边挨着-连着同一个点–显而易见);咱们可以先求出连接i这个点为1的边的数量a,为0的边的数量b,那么a*(a-1)/2,和b*(b-1)/2,就是枚举i这个点为重要点,且这个点连接的两条边都相等num1=b*(b-1)/2+a*(a-1)/2,就是所有三角形有一个点为连着的两条边相同的数量(这里先把重的三角形算入),根据上面的描述,这个答案包含着所有三角形;令num2=a*b,代表有一个点左右两边的边不相等的数量,因为一个第二种三角型中有两个这样点的,所有要除以2,所有num1-num2/2,就是三条边都相等的三角形的数量,但是因为这个三角形三个点都一模一样,所以算出来的答案除以三就是正确答案。
主要:要开longlong ,题目中会超int。

#include <bits/stdc++.h>

using namespace std;
#define int long long
namespace GenHelper {
unsigned z1, z2, z3, z4, b, u;
unsigned get() {
    b = ((z1 << 6) ^ z1) >> 13;
    z1 = ((z1 & 4294967294U) << 18) ^ b;
    b = ((z2 << 2) ^ z2) >> 27;
    z2 = ((z2 & 4294967288U) << 2) ^ b;
    b = ((z3 << 13) ^ z3) >> 21;
    z3 = ((z3 & 4294967280U) << 7) ^ b;
    b = ((z4 << 3) ^ z4) >> 12;
    z4 = ((z4 & 4294967168U) << 13) ^ b;
    return (z1 ^ z2 ^ z3 ^ z4);
}
bool read() {
    while (!u) u = get();
    bool res = u & 1;
    u >>= 1;
    return res;
}
void srand(int x) {
    z1 = x;
    z2 = (~x) ^ 0x233333333U;
    z3 = x ^ 0x1234598766U;
    z4 = (~x) + 51;
    u = 0;
}
}  // namespace GenHelper

using namespace GenHelper;
bool edge[8005][8005];
int num[8005];

signed main() {
    int n, seed;
    cin >> n >> seed;
    srand(seed);
    for (int i = 0; i < n; i++)
        for (int j = i + 1; j < n; j++) edge[j][i] = edge[i][j] = read();
    int res = 0, a = 0, b = 0;
    for (int i = 0; i < n; i++) {
        int n1 = 0, n0 = 0;
        for (int j = 0; j < n; j++) {
            if (i == j) continue;
            if (edge[i][j])
                n1++;
            else if (!edge[i][j])
                n0++;
        }
        a += n0 * (n0 - 1) / 2 + n1 * (n1 - 1) / 2;
        b += n0 * n1;
    }
    
    res = (a - b / 2) / 3;
    cout << res << endl;
    return 0;
}

标签:int,++,牛客,edge,训练赛,n0,三角形,Counting,z1
来源: https://blog.csdn.net/Are_you_ready/article/details/119086359

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有