Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/svg/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C 图的边_C - Fatal编程技术网

C 图的边

C 图的边,c,C,假设我们有一个有n个顶点的图(1如果OP的代码确实正确,那么顶点标签k不是唯一的,许多不同的顶点可以有相同的标签 假设您有一个包含100002个无符号整数的数组n,编号范围为0到100001(含0到100001),每个能够表示0到5000之间的值。将它们全部初始化为零 添加标记为k的顶点时,递增无符号整数n[k]。如果n[k-1]+n[k+1]非零,则添加此顶点会创建许多新边 如果计算创建的边数,则在添加最后一个顶点后会立即得到结果 如果顶点标签是唯一的,但可能(错误地)存在要忽略的重复标签k

假设我们有一个有n个顶点的图(1如果OP的代码确实正确,那么顶点标签k不是唯一的,许多不同的顶点可以有相同的标签

假设您有一个包含100002个无符号整数的数组n,编号范围为0到100001(含0到100001),每个能够表示0到5000之间的值。将它们全部初始化为零

添加标记为k的顶点时,递增无符号整数n[k]。如果n[k-1]+n[k+1]非零,则添加此顶点会创建许多新边

如果计算创建的边数,则在添加最后一个顶点后会立即得到结果


如果顶点标签是唯一的,但可能(错误地)存在要忽略的重复标签k,则:

假设您有一个100002个标志的数组,编号从0到100001(包括0到100001),并初始化为“全部清除”

每当您看到标记为k的顶点时,请检查是否已设置标志k。如果已设置,则这是一个要忽略的重复标志

否则,设置标志,并检查标志k-1和k+1。如果设置了其中一个标志,则创建了一条新边;如果设置了两个标志,则创建了两条新边。如果两者都清除,则不创建新边


如果计算创建的边数,添加最后一个顶点后会立即得到结果。

我终于找到了一个好的算法。谢谢您的帮助。 这是我的密码:

#include<stdio.h>
int main(){
long long int a[100000],b[100002]={0},n,i,j,edge=0;
scanf("%lld",&n);
for(i=0;i<n;i++){
    scanf("%lld",&a[i]);
    b[a[i]]++;
}
for(i=1;i<100002;i++){
    edge=edge+b[i]*b[i-1];
}
printf("%lld",edge);
}
#包括
int main(){
长整型a[100000],b[100002]={0},n,i,j,边=0;
scanf(“%lld”、&n);

对于(i=0;i(a)
a
为什么要声明
a[100000]
,而其索引是顶点名称,范围从1到5000?(b)您知道可以对数组
a
做些什么,以便更容易地查找值相近的元素吗?(c)或者,如果你有一个100000个元素的数组,你是否可以使用它来方便地找到紧密相连的顶点标签?也许我们可以对数组中的元素进行排序,但我不知道它如何帮助我们找到更快的算法。对标签进行排序会给你提供很强的约束,让你可以为这些元素找到值
i
j
使得
abs(a[i]-a[j])==1
。使用这些约束,可以在
a
的一次遍历中计算边数。如果您了解时间复杂性,整个过程可以在线性时间而不是二次时间内完成(您的算法)@b.j:啊,我看到你的代码使用0到4999,而你的问题是1-5000。你应该注意问题的说明与代码匹配,反之亦然。@b.j:你应该回答我的问题(b)和(c)。它们是线索。这取决于标签代表什么。OP提到顶点索引是它们的“名称”。“标签”可以是指“所附资料",不一定是唯一的。@Nelfeal:根据标签所代表的内容,我将其一分为二。@NominalAnimal谢谢您的帮助;您能根据您的想法发布代码吗?因为我在编写代码时遇到了麻烦。@b.j:我验证了第一个描述对于相同的输入产生的结果与您的代码相同。即使进行了完整的错误检查,代码不到25行。你可以试着用我上面的描述自己写它吗?我不打算发布解决方案,冒着你复制粘贴并作为自己的作品呈现的风险,甚至不了解代码是如何工作的。我不喜欢这样。我只喜欢帮助人们学习。
#include<stdio.h>
int main(){
long long int a[100000],b[100002]={0},n,i,j,edge=0;
scanf("%lld",&n);
for(i=0;i<n;i++){
    scanf("%lld",&a[i]);
    b[a[i]]++;
}
for(i=1;i<100002;i++){
    edge=edge+b[i]*b[i-1];
}
printf("%lld",edge);
}