C++ 计算相似点的链接总数
假设我有一组10000个点,它们彼此随机连接。例如,让我们拿10分。他们像照片一样联系在一起- 相似点的定义: 链接数相同的点称为类似点。从图中我们可以看到- 节点1与节点[2]和[10]连接 节点2与节点[1}、[3]、[4]、[5]、[6]、[7]、[8]连接 节点3仅与节点[2]连接 节点4仅与节点[2]连接 节点5仅与节点[2]连接 节点6仅与节点[2]连接 节点7仅与节点[2]连接 节点8与节点[2]和[9]连接 节点9仅与节点[8]连接 节点10仅与节点[1]连接 因此根据定义,节点-3,4,5,6,7,9,10是相似的,因为它们都只有一个链接。 同样,节点-1和8是相似的,因为它们每个都有两个链接 我的问题 现在我想计算相似点的连接的总和- 节点1有8个类似的节点 对于节点1: 它连接到节点2(具有7个链接) 并且还连接到节点10(具有1链接) 对于节点8: 它连接到节点2(具有7个链接) 并且还连接到节点9(具有1链接) 因此,对于有两个链接的组,总链接数应为=7+1+7+1=16。 像这样,我想计算其他类似点的总链接 我的代码 这是我的代码。它给出了每个点的总链接的结果C++ 计算相似点的链接总数,c++,algorithm,C++,Algorithm,假设我有一组10000个点,它们彼此随机连接。例如,让我们拿10分。他们像照片一样联系在一起- 相似点的定义: 链接数相同的点称为类似点。从图中我们可以看到- 节点1与节点[2]和[10]连接 节点2与节点[1}、[3]、[4]、[5]、[6]、[7]、[8]连接 节点3仅与节点[2]连接 节点4仅与节点[2]连接 节点5仅与节点[2]连接 节点6仅与节点[2]连接 节点7仅与节点[2]连接 节点8与节点[2]和[9]连接 节点9仅与节点[8]连接 节点10仅与节点[1]连接 因此根据定义,节
#include <cstdlib>
#include <cmath>
#include <fstream>
#include <iostream>
#include <vector>
using namespace std;
struct Node {
vector< int > links_to;
Node(void){};
Node(int first_link){
links_to.push_back(first_link);
};
};
class Links : public vector<Node> {
public:
void CreateLinks(int n,int m);
void OutputNodes();
};
int RandGenerate(int max) {
return int(drand48()*double(max));
}
void CreateRandom(int *nums,int m,int max) {
bool clear;
for(int i=0;i<m;i++) {
clear=true;
while(clear) {
clear=false;
nums[i]=RandGenerate(max);
for(int j=0;j<i;j++) {
if(nums[i]==nums[j]){
clear=true;break;
}
}
}
}
}
void Links::CreateLinks(int n,int m) {
clear();
for(int i=0;i<m;i++) {
push_back(Node());
}
int edge_targets[m],nums[m];
for(int i=0;i<m;i++) {
edge_targets[i]=i;
}
vector<int> repeated_nodes;
int source=m;
while(source<n) {
push_back(Node());
Node &node=*(end()-1);
for(int i=0;i<m;i++) {
node.links_to.push_back(edge_targets[i]);
at(edge_targets[i]).links_to.push_back(source);
repeated_nodes.push_back(edge_targets[i]);
repeated_nodes.push_back(source);
}
CreateRandom(nums,m,repeated_nodes.size());
for(int i=0;i<m;i++) {
edge_targets[i]=repeated_nodes[nums[i]];
}
source++;
}
}
void Links::OutputNodes() {
for(int i=0;i<size();i++){
cout<<endl;
for(int j=0;j<at(i).links_to.size();j++){
cout<<"Node "<<(i+1)<<" is connected with ["<<(at(i).links_to[j]+1)<<"]"<<endl;
}
cout<<"For Node: "<<(i+1)<<"\t"<<"Total links: "<<at(i).links_to.size()<<endl;
}
}
int main() {
srand48(46574621);
Links network;
network.CreateLinks(10,1); //(nodes,minimum value of link)
network.OutputNodes();
return 0;
}
我想添加一个函数,这样它可以对相似的点进行分组,并给出每个组的总链接的输出。我该如何做
根据Pixelchemist的回答进行更新
假设我将数据存储在一个文件名“MyLinks.txt”中,如下所示-
1 2
1 10
2 1
2 3
2 4
2 5
2 6
2 7
2 8...etc
并从文件中获取输入-
int main (void)
{
ifstream inputFile("MyLinks.txt");
double Temp[2];
Links links_object;
while (true) {
for (unsigned i = 0; i < 2; i++){
inputFile>>Temp[i];
}
for (size_t i(0u); i<10; ++i)
{
links_object.add(Node());
}
links_object.link_nodes(Temp[0], Temp[1]);
/*
links_object.link_nodes(0u, 9u);
links_object.link_nodes(1u, 2u);
links_object.link_nodes(1u, 3u);
links_object.link_nodes(1u, 4u);
links_object.link_nodes(1u, 5u);
links_object.link_nodes(1u, 6u);
links_object.link_nodes(1u, 7u);
links_object.link_nodes(7u, 8u);
*/
}
std::vector<size_t> linksum;
for (auto const & node : links_object.nodes())
{
size_t const linksum_index(node.links().size()-1u);
if (linksum.size() < node.links().size())
{
size_t const nls(node.links().size());
for (size_t i(linksum.size()); i<nls; ++i)
{
linksum.push_back(0u);
}
}
for (auto linked : node.links())
{
linksum[linksum_index] += linked->links().size();
}
}
for (size_t i(0u); i<linksum.size(); ++i)
{
std::cout << "Sum of secondary links with " << i+1;
std::cout << "-link nodes is: " << linksum[i] << std::endl;
}
}
int main(无效)
{
ifstream输入文件(“MyLinks.txt”);
双温[2];
链接对象;
while(true){
for(无符号i=0;i<2;i++){
输入文件>>温度[i];
}
对于(size_t i(0u);i我将使用一个映射。链接数将是键,其值将是一个包含具有该链接数的节点ID的向量
typedef std::map<size_t,std::vector<size_t> SimilarNodeMap;
SimilarNodeMap myMap;
... // fill up the map
for (SimilarNodeMap::iterator it=mymap.begin(); it!=mymap.end(); ++it)
{
std::cout << "Nodes with " it->first << " links: ";
for ( size_t i = 0; i < second->size(); ++i )
{
std::cout << second->at(i) << std::endl;
}
}
typedef std::map您可以遍历作为“对”的一部分的节点,并将它们放入列表中。如果列表中已经存在您试图添加的元素,请不要添加它。(e.x If语句检查)然后在遍历所有元素后检查列表大小,这应该是您的链接
如果这不是你要问的,请纠正我
我确信有更好的方法可以做到这一点。我认为这一点的复杂性是O(n^2)倍。我会使用std::vector
,其中vector的索引是各个节点类型的链接数
迭代所有节点,并将对应于此节点链接数的std::vector
-条目与链接到当前节点的所有节点的链接数相加
此代码:
#include <vector>
#include <stdexcept>
class Node
{
std::vector< Node const * > m_links;
public:
Node(void) { }
void link_to (Node const &n)
{
m_links.push_back(&n);
}
std::vector< Node const * > const & links (void) const
{
return m_links;
}
};
class Links
{
std::vector<Node> m_nodes;
public:
void add (Node const &node) { m_nodes.push_back(node); }
void link_nodes (size_t node_a, size_t node_b)
{
size_t ns(m_nodes.size());
if (node_a >= ns || node_b >= ns)
{
throw std::logic_error("Requested invalid link.");
}
m_nodes[node_a].link_to(m_nodes[node_b]);
m_nodes[node_b].link_to(m_nodes[node_a]);
}
std::vector<Node> const & nodes (void) const
{
return m_nodes;
}
};
int main (void)
{
Links links_object;
for (size_t i(0u); i<10; ++i)
{
links_object.add(Node());
}
links_object.link_nodes(0u, 1u);
links_object.link_nodes(0u, 9u);
links_object.link_nodes(1u, 2u);
links_object.link_nodes(1u, 3u);
links_object.link_nodes(1u, 4u);
links_object.link_nodes(1u, 5u);
links_object.link_nodes(1u, 6u);
links_object.link_nodes(1u, 7u);
links_object.link_nodes(7u, 8u);
std::vector<size_t> linksum;
for (auto const & node : links_object.nodes())
{
size_t const linksum_index(node.links().size()-1u);
if (linksum.size() < node.links().size())
{
size_t const nls(node.links().size());
for (size_t i(linksum.size()); i<nls; ++i)
{
linksum.push_back(0u);
}
}
for (auto linked : node.links())
{
linksum[linksum_index] += linked->links().size();
}
}
for (size_t i(0u); i<linksum.size(); ++i)
{
std::cout << "Sum of secondary links with " << i+1;
std::cout << "-link nodes is: " << linksum[i] << std::endl;
}
}
#包括
#包括
类节点
{
std::向量m_链接;
公众:
节点(空){}
无效链接到(节点常量(&n)
{
m_链接。将_向后推(&n);
}
标准::向量<节点常数*>常数和链接(无效)常数
{
返回m_链接;
}
};
类链接
{
std::向量m_节点;
公众:
void add(Node const&Node){m_nodes.push_back(Node);}
无效链接节点(大小节点a、大小节点b)
{
大小(m_nodes.size());
如果(节点a>=ns | |节点b>=ns)
{
抛出std::logic_错误(“请求的无效链接”);
}
m_节点[node_a]。链接到(m_节点[node_b]);
m_节点[node_b]。链接到(m_节点[node_a]);
}
std::向量常量和节点(void)常量
{
返回m_节点;
}
};
内部主(空)
{
链接对象;
对于(size_t i(0u);i您可以迭代所有节点并计数。
伪代码:
std::map<std::size_t, std::size_t> counter;
for each node
++counter[node.links().size]
std::map计数器;
对于每个节点
++计数器[节点.链接().大小]
我想计算大约10000个节点。因此,if语句检查可能不是一个好主意,因为我无法判断每个节点将创建多少个链接。我想检查大约10000个点。因此我将数据存储在文本文件中,并尝试从中获取值并在代码中使用。但我遇到了分段错误。我已更新我的代码。请检查。我如何修复它?@aries0152为什么要进行文件I/o?我想检查大约10000个节点。每个节点都使用links\u object.link\u节点(0u,1u);因此我认为我将值存储在文本文件中,并在links\u object.link\u节点(0u,1u);(实际上是我的想法)。请您帮助我,在不为每个节点指定链接对象的情况下,如何使用您的代码?这些节点来自何处?如何确定其中哪些节点是链接的?假设您从最小的m0节点开始。新节点一次添加一个。每个新节点都连接到m
Sum of secondary links with 1-link nodes is: 39
Sum of secondary links with 2-link nodes is: 16
Sum of secondary links with 3-link nodes is: 0
Sum of secondary links with 4-link nodes is: 0
Sum of secondary links with 5-link nodes is: 0
Sum of secondary links with 6-link nodes is: 0
Sum of secondary links with 7-link nodes is: 9
std::map<std::size_t, std::size_t> counter;
for each node
++counter[node.links().size]