Change graph edges structure to adjacency
This commit is contained in:
parent
e7888956a8
commit
b9f8695996
@ -7,16 +7,34 @@ namespace Assets.Map
|
|||||||
public class Graph<T>
|
public class Graph<T>
|
||||||
{
|
{
|
||||||
public List<T> Vertices { get; internal set; } = new List<T>();
|
public List<T> Vertices { get; internal set; } = new List<T>();
|
||||||
public ISet<(int, int)> Edges { get; internal set; } = new HashSet<(int, int)>();
|
public Dictionary<int, List<int>> _edges = new Dictionary<int, List<int>>();
|
||||||
|
|
||||||
|
public IEnumerable<(int, int)> Edges
|
||||||
|
{
|
||||||
|
get
|
||||||
|
{
|
||||||
|
return _edges.SelectMany(pair => pair.Value.Where(value => value > pair.Key).Select(value => (pair.Key, value)));
|
||||||
|
}
|
||||||
|
|
||||||
|
set
|
||||||
|
{
|
||||||
|
_edges = new Dictionary<int, List<int>>();
|
||||||
|
|
||||||
|
foreach (var (a, b) in value)
|
||||||
|
AddEdge(a, b);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public void AddEdge(int a, int b)
|
public void AddEdge(int a, int b)
|
||||||
{
|
{
|
||||||
Edges.Add(a < b ? (a, b) : (b, a));
|
if (!_edges.ContainsKey(a))
|
||||||
}
|
_edges[a] = new List<int>();
|
||||||
|
|
||||||
public IEnumerable<(int, int)> EdgesOf(int a)
|
if (!_edges.ContainsKey(b))
|
||||||
{
|
_edges[b] = new List<int>();
|
||||||
return Edges.Where(x => x.Item1 == a || x.Item2 == a);
|
|
||||||
|
_edges[a].Add(b);
|
||||||
|
_edges[b].Add(a);
|
||||||
}
|
}
|
||||||
|
|
||||||
public Graph<U> Morph<U>(Func<T, U> morph)
|
public Graph<U> Morph<U>(Func<T, U> morph)
|
||||||
@ -30,8 +48,9 @@ namespace Assets.Map
|
|||||||
|
|
||||||
public IEnumerable<int> Neighbours(int vertex)
|
public IEnumerable<int> Neighbours(int vertex)
|
||||||
{
|
{
|
||||||
foreach (var (a, b) in this.EdgesOf(vertex))
|
if (!_edges.ContainsKey(vertex)) return Enumerable.Empty<int>();
|
||||||
yield return a == vertex ? b : a;
|
|
||||||
|
return _edges[vertex];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -1,6 +1,5 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
|
||||||
using Assets.Voronoi;
|
using Assets.Voronoi;
|
||||||
using Random = System.Random;
|
using Random = System.Random;
|
||||||
|
|
||||||
@ -12,7 +11,6 @@ namespace Assets.Map
|
|||||||
private readonly Graph<Location> _locations;
|
private readonly Graph<Location> _locations;
|
||||||
|
|
||||||
private readonly List<(int, Location)> _queue = new List<(int, Location)>();
|
private readonly List<(int, Location)> _queue = new List<(int, Location)>();
|
||||||
private readonly Dictionary<Location, List<int>> _blacklist = new Dictionary<Location, List<int>>();
|
|
||||||
|
|
||||||
private readonly Random _random;
|
private readonly Random _random;
|
||||||
|
|
||||||
@ -20,7 +18,6 @@ namespace Assets.Map
|
|||||||
public Graph<Location> Result => _locations;
|
public Graph<Location> Result => _locations;
|
||||||
|
|
||||||
public bool Done => _queue.Count == 0;
|
public bool Done => _queue.Count == 0;
|
||||||
|
|
||||||
|
|
||||||
public LocationGenerator(List<Location> locations, Graph<Site> sites, Random random = null)
|
public LocationGenerator(List<Location> locations, Graph<Site> sites, Random random = null)
|
||||||
{
|
{
|
||||||
@ -32,11 +29,7 @@ namespace Assets.Map
|
|||||||
|
|
||||||
public void SetLocation(int vertex, Location location)
|
public void SetLocation(int vertex, Location location)
|
||||||
{
|
{
|
||||||
_sites.Vertices[vertex].Location = location;
|
location.AddSite(_sites.Vertices[vertex]);
|
||||||
location.Sites.Add(_sites.Vertices[vertex]);
|
|
||||||
|
|
||||||
FixBoundaryPoints(vertex, location);
|
|
||||||
FixBoundaryEdges(vertex, location);
|
|
||||||
|
|
||||||
foreach (var neighbour in _sites.Neighbours(vertex))
|
foreach (var neighbour in _sites.Neighbours(vertex))
|
||||||
if (_sites.Vertices[neighbour].Location == null)
|
if (_sites.Vertices[neighbour].Location == null)
|
||||||
@ -75,24 +68,5 @@ namespace Assets.Map
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void FixBoundaryPoints(int vertex, Location location)
|
|
||||||
{
|
|
||||||
var a = location.BoundaryPoints;
|
|
||||||
var b = _sites.Vertices[vertex].Site.Vertices;
|
|
||||||
|
|
||||||
if (!_blacklist.ContainsKey(location)) _blacklist[location] = new List<int>();
|
|
||||||
_blacklist[location].AddRange(a.Intersect(b));
|
|
||||||
|
|
||||||
location.BoundaryPoints = a.Union(b).Except(_blacklist[location]).ToList();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void FixBoundaryEdges(int vertex, Location location)
|
|
||||||
{
|
|
||||||
var a = location.BoundaryEdges;
|
|
||||||
var b = _sites.Vertices[vertex].Site.Edges;
|
|
||||||
|
|
||||||
location.BoundaryEdges = a.Union(b).Except(a.Intersect(b)).ToList();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -1,4 +1,6 @@
|
|||||||
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
using Assets.Common;
|
using Assets.Common;
|
||||||
using Assets.Voronoi;
|
using Assets.Voronoi;
|
||||||
using UnityEngine;
|
using UnityEngine;
|
||||||
@ -8,10 +10,30 @@ namespace Assets.Map
|
|||||||
public class Location
|
public class Location
|
||||||
{
|
{
|
||||||
public List<LocationSite> Sites = new List<LocationSite>();
|
public List<LocationSite> Sites = new List<LocationSite>();
|
||||||
public List<int> BoundaryPoints = new List<int>();
|
|
||||||
|
public IEnumerable<int> Points => Sites.SelectMany(site => site.Site.Vertices);
|
||||||
|
public IEnumerable<int> BoundaryPoints => BoundaryEdges.SelectMany(edge => new [] { edge.Item1, edge.Item2 }).Distinct();
|
||||||
|
public IEnumerable<int> InsidePoints => Points.Except(BoundaryPoints);
|
||||||
|
|
||||||
public List<(int, int)> BoundaryEdges = new List<(int, int)>();
|
public List<(int, int)> BoundaryEdges = new List<(int, int)>();
|
||||||
|
|
||||||
public LocationType Type;
|
public LocationType Type;
|
||||||
|
|
||||||
|
public void AddSite(LocationSite site)
|
||||||
|
{
|
||||||
|
site.Location = this;
|
||||||
|
Sites.Add(site);
|
||||||
|
|
||||||
|
FixBoundaryEdges(site);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void FixBoundaryEdges(LocationSite site)
|
||||||
|
{
|
||||||
|
var a = BoundaryEdges;
|
||||||
|
var b = site.Site.Edges;
|
||||||
|
|
||||||
|
BoundaryEdges = a.Union(b).Except(a.Intersect(b)).ToList();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public class LocationSite
|
public class LocationSite
|
||||||
|
Loading…
Reference in New Issue
Block a user