using System;
using System.Collections.Generic;
using System.Text;
namespace Framework.Collections
{
///
/// The EdgeWeightedDigrpah class represents an edge-weighted directed graph of vertices named 0 through V-1, where each directed edge
/// is of type DirectedEdge and has real-valued weight.
///
/// EdgeWeightedDigraph class from Princeton University's Java Algorithms
public class EdgeWeightedDigraph
{
private readonly LinkedList[] _adjacent;
///
/// Constructs an empty edge-weighted digraph with the specified number of vertices and 0 edges
///
/// Number of vertices in the Graph
public EdgeWeightedDigraph(int vertices)
{
NumberOfVertices = vertices;
NumberOfEdges = 0;
_adjacent = new LinkedList[NumberOfVertices];
for (int v = 0; v < NumberOfVertices; v++)
{
_adjacent[v] = new LinkedList();
}
}
///
/// The number of vertices in the edge-weighted digraph
///
public int NumberOfVertices { get; private set; }
///
/// The number of edges in the edge-weighted digraph
///
public int NumberOfEdges { get; private set; }
///
/// Adds the specified directed edge to the edge-weighted digraph
///
/// The DirectedEdge to add
/// DirectedEdge cannot be null
public void AddEdge(DirectedEdge edge)
{
if (edge == null)
{
throw new ArgumentNullException("edge", "DirectedEdge cannot be null");
}
_adjacent[edge.From].AddLast(edge);
}
///
/// Returns an IEnumerable of the DirectedEdges incident from the specified vertex
///
/// The vertex to find incident DirectedEdges from
/// IEnumerable of the DirectedEdges incident from the specified vertex
public IEnumerable Adjacent(int vertex)
{
return _adjacent[vertex];
}
///
/// Returns an IEnumerable of all directed edges in the edge-weighted digraph
///
/// IEnumerable of of all directed edges in the edge-weighted digraph
public IEnumerable Edges()
{
for (int v = 0; v < NumberOfVertices; v++)
{
foreach (DirectedEdge edge in _adjacent[v])
{
yield return edge;
}
}
}
///
/// Returns the number of directed edges incident from the specified vertex
/// This is known as the outdegree of the vertex
///
/// The vertex to find find the outdegree of
/// The number of directed edges incident from the specified vertex
public int OutDegree(int vertex)
{
return _adjacent[vertex].Count;
}
///
/// Returns a string that represents the current edge-weighted digraph
///
///
/// A string that represents the current edge-weighted digraph
///
public override string ToString()
{
var formattedString = new StringBuilder();
formattedString.AppendFormat("{0} vertices, {1} edges {2}", NumberOfVertices, NumberOfEdges, Environment.NewLine);
for (int v = 0; v < NumberOfVertices; v++)
{
formattedString.AppendFormat("{0}: ", v);
foreach (DirectedEdge edge in _adjacent[v])
{
formattedString.AppendFormat("{0} ", edge.To);
}
formattedString.AppendLine();
}
return formattedString.ToString();
}
}
///
/// The DirectedEdge class represents a weighted edge in an edge-weighted directed graph.
///
/// DirectedEdge class from Princeton University's Java Algorithms
public class DirectedEdge
{
///
/// Constructs a directed edge from one specified vertex to another with the given weight
///
/// The start vertex
/// The destination vertex
/// The weight of the DirectedEdge
public DirectedEdge(uint from, uint to, double weight)
{
From = from;
To = to;
Weight = weight;
}
///
/// Returns the destination vertex of the DirectedEdge
///
public uint From { get; private set; }
///
/// Returns the start vertex of the DirectedEdge
///
public uint To { get; private set; }
///
/// Returns the weight of the DirectedEdge
///
public double Weight { get; private set; }
///
/// Returns a string that represents the current DirectedEdge
///
///
/// A string that represents the current DirectedEdge
///
public override string ToString()
{
return $"From: {From}, To: {To}, Weight: {Weight}";
}
}
}