这个问题是关于找到一个LINQ-Query,它从任何给定节点到任何其他给定节点提取非循环图中的路径。
请注意这只是关于LINQ(证明其权力或显示其局限性)
假设以下类表示图G = (V,E)
DataStruc
internal class Vertice
{
private Int32 id;
public Vertice(Int32 id)
{
this.id = id;
}
public Int32 GetId()
{
return this.id;
}
}
internal class Edge
{
private Int32 id;
private Vertice v1;
private Vertice v2;
public Edge(Int32 id, Vertice v1, Vertice v2)
{
this.id = id;
this.v1 = v1;
this.v2 = v2;
}
public Vertice GetFirstVertice()
{
return this.v1;
}
public Vertice GetSecondVertice()
{
return this.v2;
}
public Int32 GetId()
{
return this.id;
}
public Boolean ConnectedTo(Vertice v)
{
if (v.GetId() == this.v1.GetId()) return true;
if (v.GetId() == this.v2.GetId()) return true;
return false;
}
public Boolean Connects(Vertice u, Vertice v)
{
if (!this.ConnectedTo(u)) return false;
if (!this.ConnectedTo(v)) return false;
return true;
}
}
现在使用图片下方显示的代码创建一个图形(是的,图片显示了一个有向图,但现在让我们忽略它)
创建图表的代码
// Create Vertices
List<Vertice> v = new List<Vertice>();
v.Add(new Vertice(0));
v.Add(new Vertice(1));
v.Add(new Vertice(2));
v.Add(new Vertice(3));
v.Add(new Vertice(4));
// Create Edges
List<Edge> e = new List<Edge>();
e.Add(new Edge(0, v[0], v[1]));
e.Add(new Edge(1, v[1], v[2]));
e.Add(new Edge(2, v[1], v[3]));
e.Add(new Edge(3, v[1], v[4]));
e.Add(new Edge(4, v[2], v[4]));
现在让我们查询图表(v,e)
查询从v0提取所有边缘到v1
var edge_query =
from edge in e
where edge.Connects(v[0], v[1])
select edge;
执行查询只给出一条边(id = 0)。我现在很好奇是否可以编写返回多组边的LINQ查询,其中每个集包含从给定节点u
到另一个给定节点v
的一条路径
以下是可以粘贴到ConsoleApplication
。
亲切的问候, BENJ
using System;
using System.Collections.Generic;
using System.Linq;
namespace StackOverflow
{
class Program
{
static void Main(string[] args)
{
// Create Vertices
List<Vertice> v = new List<Vertice>();
v.Add(new Vertice(0));
v.Add(new Vertice(1));
v.Add(new Vertice(2));
v.Add(new Vertice(3));
v.Add(new Vertice(4));
// Create Edges
List<Edge> e = new List<Edge>();
e.Add(new Edge(0, v[0], v[1]));
e.Add(new Edge(1, v[1], v[2]));
e.Add(new Edge(2, v[1], v[3]));
e.Add(new Edge(3, v[1], v[4]));
e.Add(new Edge(4, v[2], v[4]));
// Query Set
var edge_query =
from edge in e
where edge.Connects(v[0], v[1])
select edge;
foreach (Edge edge in edge_query)
{
Console.WriteLine("e" + edge.GetId() + " connects v" + edge.GetFirstVertice().GetId() + " and v" + edge.GetSecondVertice().GetId());
}
// Wait for the user to understand
Console.WriteLine();
Console.WriteLine("[ENTER] to terminate ...");
Console.ReadLine();
}
internal class Vertice
{
private Int32 id;
public Vertice(Int32 id)
{
this.id = id;
}
public Int32 GetId()
{
return this.id;
}
}
internal class Edge
{
private Int32 id;
private Vertice v1;
private Vertice v2;
public Edge(Int32 id, Vertice v1, Vertice v2)
{
this.id = id;
this.v1 = v1;
this.v2 = v2;
}
public Vertice GetFirstVertice()
{
return this.v1;
}
public Vertice GetSecondVertice()
{
return this.v2;
}
public Int32 GetId()
{
return this.id;
}
public Boolean ConnectedTo(Vertice v)
{
if (v.GetId() == this.v1.GetId()) return true;
if (v.GetId() == this.v2.GetId()) return true;
return false;
}
public Boolean Connects(Vertice u, Vertice v)
{
if (!this.ConnectedTo(u)) return false;
if (!this.ConnectedTo(v)) return false;
return true;
}
}
}
}
编辑1
即。将Edge.Connects
- 方法更改为
public Boolean Connects(Vertice u, Vertice v)
{
if (this.v1.GetId() != u.GetId()) return false;
if (this.v2.GetId() != v.GetId()) return false;
return true;
}
可以使用查询
var edge_query =
from u1 in v
from edge1 in e
from edge2 in e
where edge1.Connects(v_start, u1)
where edge2.Connects(u1, v_stop)
select new Tuple<Edge, Edge>(edge1, edge2);
通过V中的任何顶点v_start
提取从v_stop
到u1
的所有路径,是否可以扩展查询以考虑任意数量的中间顶点?