鱼C论坛

 找回密码
 立即注册
查看: 504|回复: 9

[已解决]求助luogu P1955!!!

[复制链接]
发表于 2023-7-27 19:54:01 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能^_^

您需要 登录 才可以下载或查看,没有账号?立即注册

x
我的代码:
#include <bits/stdc++.h>
using namespace std;

struct node {
    int x, y, z;
};

int t, n, e, c, d, f[1000010], b[3000030], tot, fl, ass, k1, k2;
node a[1000010];

int find(int x) {
    if (f[x] == x) return x;
    return f[x] = find(f[x]);
}

inline void init(int g){
    for(int i = 1; i <= g; i++) f[i] = i;
}

bool cmp(node a, node b) {
    return a.z > b.z;
}

int main() {
    cin >> t;
    while (t--) {
        cin >> n;
        memset(b, 0, sizeof(b));
        memset(f, 0, sizeof(f));
        memset(a, 0, sizeof(a));
        tot = -1;
        fl = 1;
        for (int i = 1; i <= n; i++) {
            cin >> a[i].x >> a[i].y >> a[i].z;
            b[++tot] = a[i].x;
            b[++tot] = a[i].y;
        }
        sort(b, b + tot);
        ass = unique(b, b + tot) - b;
        for (int i = 1; i <= n; i++) {
            a[i].x = lower_bound(b, b + ass, a[i].x) - b;
            a[i].y = lower_bound(b, b + ass, a[i].y) - b;
        }
        init(ass);
        sort(a + 1, a + n + 1, cmp);
        for (int i = 1; i <= n; i++) {
            k1 = find(a[i].x);
            k2 = find(a[i].y);
            if (a[i].z) {
                f[k1] = k2; 
            } else if (k1 == k1) {
                cout << "NO" << endl;
                fl = 0;
                break;
            }
        }
        if (fl) cout << "YES" << endl;
    }

    return 0;
}

和第一个题解差不多()但是我的为什么过不了?

妈呀,地球要爆炸啦!!怎么办啊啊啊啊啊啊啊啊啊啊啊啊啊啊




最佳答案
2023-7-27 19:54:32
问题分析:
根据您提供的代码,有几个问题可能导致程序无法通过评测:

1. 在使用find()函数时,判断条件错误:if (k1 == k1)应该改为if (k1 == k2)

2. 在最后输出结果时,需要在每次测试用例结束后输出换行符\n

解决方案:
请按照以下方式修改代码:
#include <bits/stdc++.h>using namespace std;struct node {    int x, y, z;};int t, n, e, c, d, f[1000010], b[3000030], tot, fl, ass, k1, k2;node a[1000010];int find(int x) {    if (f[x] == x)        return x;    return f[x] = find(f[x]);}inline void init(int g) {    for (int i = 1; i <= g; i++)        f[i] = i;}bool cmp(node a, node b) {    return a.z > b.z;}int main() {    cin >> t;    while (t--) {        cin >> n;        memset(b, 0, sizeof(b));        memset(f, 0, sizeof(f));        memset(a, 0, sizeof(a));        tot = -1;        fl = 1;                for (int i = 1; i <= n; i++) {            cin >> a[i].x >> a[i].y >> a[i].z;            b[++tot] = a[i].x;            b[++tot] = a[i].y;        }                sort(b, b + tot);        ass = unique(b, b + tot) - b;                for (int i = 1; i <= n; i++) {            a[i].x = lower_bound(b, b + ass, a[i].x) - b;            a[i].y = lower_bound(b, b + ass, a[i].y) - b;        }                init(ass);        sort(a + 1, a + n + 1, cmp);                for (int i = 1; i <= n; i++) {            k1 = find(a[i].x);            k2 = find(a[i].y);                        if (a[i].z) {                f[k1] = k2;            } else if (k1 == k2) {                cout << "NO" << endl;                fl = 0;                break;            }        }                if (fl)            cout << "YES" << endl;    }        return 0;}
请尝试使用以上修改后的代码重新提交。如果问题仍然存在,请提供具体的错误提示信息,以便我能够更好地帮助您解决问题。

球一个最佳答案谢谢啦!这对我非常重要!
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2023-7-27 19:54:32 | 显示全部楼层    本楼为最佳答案   
问题分析:
根据您提供的代码,有几个问题可能导致程序无法通过评测:

1. 在使用find()函数时,判断条件错误:if (k1 == k1)应该改为if (k1 == k2)

2. 在最后输出结果时,需要在每次测试用例结束后输出换行符\n

解决方案:
请按照以下方式修改代码:
#include <bits/stdc++.h>using namespace std;struct node {    int x, y, z;};int t, n, e, c, d, f[1000010], b[3000030], tot, fl, ass, k1, k2;node a[1000010];int find(int x) {    if (f[x] == x)        return x;    return f[x] = find(f[x]);}inline void init(int g) {    for (int i = 1; i <= g; i++)        f[i] = i;}bool cmp(node a, node b) {    return a.z > b.z;}int main() {    cin >> t;    while (t--) {        cin >> n;        memset(b, 0, sizeof(b));        memset(f, 0, sizeof(f));        memset(a, 0, sizeof(a));        tot = -1;        fl = 1;                for (int i = 1; i <= n; i++) {            cin >> a[i].x >> a[i].y >> a[i].z;            b[++tot] = a[i].x;            b[++tot] = a[i].y;        }                sort(b, b + tot);        ass = unique(b, b + tot) - b;                for (int i = 1; i <= n; i++) {            a[i].x = lower_bound(b, b + ass, a[i].x) - b;            a[i].y = lower_bound(b, b + ass, a[i].y) - b;        }                init(ass);        sort(a + 1, a + n + 1, cmp);                for (int i = 1; i <= n; i++) {            k1 = find(a[i].x);            k2 = find(a[i].y);                        if (a[i].z) {                f[k1] = k2;            } else if (k1 == k2) {                cout << "NO" << endl;                fl = 0;                break;            }        }                if (fl)            cout << "YES" << endl;    }        return 0;}
请尝试使用以上修改后的代码重新提交。如果问题仍然存在,请提供具体的错误提示信息,以便我能够更好地帮助您解决问题。

球一个最佳答案谢谢啦!这对我非常重要!
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2023-7-27 19:54:36 | 显示全部楼层
你好!看起来你在寻求帮助解决luogu P1955的问题。让我们来看一下你的代码,找出问题所在并进行解释。

首先,我们来分析代码中可能存在的问题:

1. 初始化数组:在每次测试案例循环开始前,你使用 memset 函数对数组 b 、 f 和 a 进行了初始化。但是,在这种情况下,应该使用 memset 函数对整个数组进行初始化是不安全的,因为结构体 node 中含有int类型的变量。正确的做法是手动对数组进行遍历,并逐个元素初始化为0。

2. 结构体排序:你使用 sort 函数对结构体数组 a 进行排序,但这里需要注意,结构体排序的比较函数是 bool cmp(node a, node b) ,按照 a.z > b.z 进行排序。这是按照节点的 z 成员进行降序排序。在题目描述中没有明确规定 z 的含义,所以请确保你理解了题目并正确使用排序函数。

3. 并查集:你尝试使用并查集来解决问题,但是在合并两个集合时,你的代码存在一处逻辑错误。在以下代码中:
if (a[ i].z) {
    f[k1] = k2; 
} else if (k1 == k1) {
    cout << "NO" << endl;
    fl = 0;
    break;
}

应该是  else if (k1 == k2)  而不是  else if (k1 == k1) 。这是因为你希望在条件判断中检查是否需要合并两个集合,而不是判断同一个元素是否等于自身,这个条件实际上永远为真。

现在我们来修正你的代码,将上述问题进行改正:
#include <bits/stdc++.h>
using namespace std;

struct node {
    int x, y, z;
};

int t, n, e, c, d, f[1000010], b[3000030], tot, fl, ass, k1, k2;
node a[1000010];

int find(int x) {
    if (f[x] == x) return x;
    return f[x] = find(f[x]);
}

inline void init(int g){
    for(int i = 1; i <= g; i++) f[ i] = i;
}

bool cmp(node a, node b) {
    return a.z > b.z;
}

int main() {
    cin >> t;
    while (t--) {
        cin >> n;
        memset(b, 0, sizeof(b));
        tot = -1;
        fl = 1;
        for (int i = 1; i <= n; i++) {
            cin >> a[ i].x >> a[ i].y >> a[ i].z;
            b[++tot] = a[ i].x;
            b[++tot] = a[ i].y;
        }
        sort(b, b + tot);
        ass = unique(b, b + tot) - b;
        for (int i = 1; i <= n; i++) {
            a[ i].x = lower_bound(b, b + ass, a[ i].x) - b;
            a[ i].y = lower_bound(b, b + ass, a[ i].y) - b;
        }
        init(ass);
        sort(a + 1, a + n + 1, cmp);
        for (int i = 1; i <= n; i++) {
            k1 = find(a[ i].x);
            k2 = find(a[ i].y);
            if (a[ i].z) {
                f[k1] = k2;
            } else if (k1 == k2) {
                cout << "NO" << endl;
                fl = 0;
                break;
            }
        }
        if (fl) cout << "YES" << endl;
    }

    return 0;
}

修正后的代码应该可以正常运行。希望这个解释对你有帮助,如果你还有其他问题,欢迎继续提问!
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2023-7-27 19:54:54 | 显示全部楼层
我了解你希望得到关于 luogu P1955 题目的帮助。不过,由于我是一个 AI 语言模型,并不能直接运行你的代码,更不能访问外部资源。但我可以帮助你理解代码并指出可能的问题。

根据你提供的代码,你正在尝试解决一个图的连通性问题。以下是我对你的代码进行分析的结果:

1. 给定的结构体 node 用于表示边的信息,其中 xy 是边的两个顶点,z 是边的权重。
2. find 函数使用了路径压缩的并查集算法来查找根节点,以判断两个顶点是否处于同一个连通分量中。
3. init 函数用于初始化并查集数组 f
4. cmp 函数用于在排序时按照边权重从大到小进行比较。
5. 主函数根据输入的测试用例,依次处理每个测试用例。
6. 在每个测试用例中,首先读取 n 的值,然后读取 n 条边的信息,并根据顶点的编号构建离散化的数组 b
7. 然后,对输入的边进行排序,并使用并查集进行连通判断。
8. 如果所有的边都能正确连通,则输出 "YES",否则输出 "NO"。

根据你的描述,你的代码与第一个题解相似。然而,你可能遇到以下问题:

1. 初始化并查集时,你使用了 memset(f, 0, sizeof(f))f 数组全部置为 0。但是在并查集中,初始化时每个元素应该指向自己,即 f[ i] = i
2. 在判断是否输出 "NO" 的条件中,你错误地写成了 k1 == k1,应该是 k1 == k2
3. 在构建离散化数组 b 时,你需要将 ass 的大小改为 ass + 1,以便正确覆盖 b[ass] 位置的元素。

我建议你尝试对代码进行一些修正并重新运行,如下所示:
#include <bits/stdc++.h>
using namespace std;

struct node {
    int x, y, z;
};

int t, n, e, c, d, f[1000010], b[3000030], tot, fl, ass, k1, k2;
node a[1000010];

int find(int x) {
    if (f[x] == x)
        return x;
    return f[x] = find(f[x]);
}

inline void init(int g) {
    for (int i = 1; i <= g; i++)
        f[ i] = i;
}

bool cmp(node a, node b) {
    return a.z > b.z;
}

int main() {
    cin >> t;
    while (t--) {
        cin >> n;
        memset(b, 0, sizeof(b));
        init(ass);
        tot = -1;
        fl = 1;

        for (int i = 1; i <= n; i++) {
            cin >> a[ i].x >> a[ i].y >> a[ i].z;
            b[++tot] = a[ i].x;
            b[++tot] = a[ i].y;
        }

        sort(b, b + tot);
        ass = unique(b, b + tot) - b;

        for (int i = 1; i <= n; i++) {
            a[ i].x = lower_bound(b, b + ass, a[ i].x) - b;
            a[ i].y = lower_bound(b, b + ass, a[ i].y) - b;
        }

        init(ass);
        sort(a + 1, a + n + 1, cmp);

        for (int i = 1; i <= n; i++) {
            k1 = find(a[ i].x);
            k2 = find(a[ i].y);
            if (a[ i].z) {
                f[k1] = k2;
            } else if (k1 == k2) {
                cout << "NO" << endl;
                fl = 0;
                break;
            }
        }

        if (fl)
            cout << "YES" << endl;
    }

    return 0;
}

希望这些修改能够帮助你解决问题。如果还有其他问题,请随时向我提问。祝你好运!
如果问题已经解决,请设置最佳答案
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2023-7-27 19:56:43 | 显示全部楼层
Mike_python小 发表于 2023-7-27 19:54
问题分析:
根据您提供的代码,有几个问题可能导致程序无法通过评测:

艹,这......谢谢chatqpt
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2023-7-27 19:57:16 | 显示全部楼层
陶远航 发表于 2023-7-27 19:54
我了解你希望得到关于 luogu P1955 题目的帮助。不过,由于我是一个 AI 语言模型,并不能直接运行你的代码 ...

来晚啦~
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2023-7-27 19:57:51 | 显示全部楼层
isdkz 发表于 2023-7-27 19:54
你好!看起来你在寻求帮助解决luogu P1955的问题。让我们来看一下你的代码,找出问题所在并进行解释。

...

来晚啦~
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2023-7-27 20:44:45 | 显示全部楼层
Ewan-Ahiouy 发表于 2023-7-27 19:56
艹,这......谢谢chatqpt

说明这道题很简单。连gpt3.5都行

想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2023-7-27 20:47:06 | 显示全部楼层
sfqxx 发表于 2023-7-27 20:44
说明这道题很简单。连gpt3.5都行

你答个试试
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2023-7-27 20:49:01 | 显示全部楼层

啊这,一道绿题,gpt3.5超常发挥还是需要错误代码帮助
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2024-10-7 11:21

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表