Switch from ReadOnlyCollections to raw arrays

This commit is contained in:
ConfusedPolarBear 2022-07-09 00:24:58 -05:00
parent 259bddfc1a
commit 2bd6c90409
4 changed files with 25 additions and 25 deletions

View File

@ -66,8 +66,8 @@ public class TestAudioFingerprinting
[Fact]
public void TestIndexGeneration()
{
// 0 1 2 3 4 5 6 7
var fpr = new List<uint>(new uint[] { 1, 2, 3, 1, 5, 77, 42, 2 }).AsReadOnly();
// 0 1 2 3 4 5 6 7
var fpr = new uint[] { 1, 2, 3, 1, 5, 77, 42, 2 };
var expected = new Dictionary<uint, int>()
{
{1, 3},

View File

@ -66,10 +66,10 @@ public static class Chromaprint
/// </summary>
/// <param name="episode">Queued episode to fingerprint.</param>
/// <returns>Numerical fingerprint points.</returns>
public static ReadOnlyCollection<uint> Fingerprint(QueuedEpisode episode)
public static uint[] Fingerprint(QueuedEpisode episode)
{
// Try to load this episode from cache before running ffmpeg.
if (LoadCachedFingerprint(episode, out ReadOnlyCollection<uint> cachedFingerprint))
if (LoadCachedFingerprint(episode, out uint[] cachedFingerprint))
{
Logger?.LogDebug("Fingerprint cache hit on {File}", episode.Path);
return cachedFingerprint;
@ -106,7 +106,7 @@ public static class Chromaprint
// Try to cache this fingerprint.
CacheFingerprint(episode, results);
return results.AsReadOnly();
return results.ToArray();
}
/// <summary>
@ -114,11 +114,11 @@ public static class Chromaprint
/// </summary>
/// <param name="fingerprint">Chromaprint fingerprint.</param>
/// <returns>Inverted index.</returns>
public static Dictionary<uint, int> CreateInvertedIndex(ReadOnlyCollection<uint> fingerprint)
public static Dictionary<uint, int> CreateInvertedIndex(uint[] fingerprint)
{
var invIndex = new Dictionary<uint, int>();
for (int i = 0; i < fingerprint.Count; i++)
for (int i = 0; i < fingerprint.Length; i++)
{
// Get the current point.
var point = fingerprint[i];
@ -183,11 +183,11 @@ public static class Chromaprint
/// Tries to load an episode's fingerprint from cache. If caching is not enabled, calling this function is a no-op.
/// </summary>
/// <param name="episode">Episode to try to load from cache.</param>
/// <param name="fingerprint">ReadOnlyCollection to store the fingerprint in.</param>
/// <param name="fingerprint">Array to store the fingerprint in.</param>
/// <returns>true if the episode was successfully loaded from cache, false on any other error.</returns>
private static bool LoadCachedFingerprint(QueuedEpisode episode, out ReadOnlyCollection<uint> fingerprint)
private static bool LoadCachedFingerprint(QueuedEpisode episode, out uint[] fingerprint)
{
fingerprint = new List<uint>().AsReadOnly();
fingerprint = Array.Empty<uint>();
// If fingerprint caching isn't enabled, don't try to load anything.
if (!(Plugin.Instance?.Configuration.CacheFingerprints ?? false))
@ -228,7 +228,7 @@ public static class Chromaprint
return false;
}
fingerprint = result.AsReadOnly();
fingerprint = result.ToArray();
return true;
}

View File

@ -103,7 +103,7 @@ public class VisualizationController : ControllerBase
/// <param name="id">Episode id.</param>
/// <returns>Read only collection of fingerprint points.</returns>
[HttpGet("Fingerprint/{Id}")]
public ActionResult<ReadOnlyCollection<uint>> GetEpisodeFingerprint([FromRoute] Guid id)
public ActionResult<uint[]> GetEpisodeFingerprint([FromRoute] Guid id)
{
var queue = Plugin.Instance!.AnalysisQueue;

View File

@ -61,7 +61,7 @@ public class FingerprinterTask : IScheduledTask
/// Temporary fingerprint cache to speed up reanalysis.
/// Fingerprints are removed from this after a season is analyzed.
/// </summary>
private Dictionary<Guid, ReadOnlyCollection<uint>> _fingerprintCache;
private Dictionary<Guid, uint[]> _fingerprintCache;
/// <summary>
/// Statistics for the currently running analysis task.
@ -92,7 +92,7 @@ public class FingerprinterTask : IScheduledTask
_logger = loggerFactory.CreateLogger<FingerprinterTask>();
_queueLogger = loggerFactory.CreateLogger<QueueManager>();
_fingerprintCache = new Dictionary<Guid, ReadOnlyCollection<uint>>();
_fingerprintCache = new Dictionary<Guid, uint[]>();
EdlManager.Initialize(_logger);
}
@ -431,9 +431,9 @@ public class FingerprinterTask : IScheduledTask
/// <returns>Intros for the first and second episodes.</returns>
public (Intro Lhs, Intro Rhs) FingerprintEpisodes(
Guid lhsId,
ReadOnlyCollection<uint> lhsPoints,
uint[] lhsPoints,
Guid rhsId,
ReadOnlyCollection<uint> rhsPoints,
uint[] rhsPoints,
bool isFirstPass)
{
// If this isn't running as part of the first analysis pass, don't count this CPU time as first pass time.
@ -468,7 +468,7 @@ public class FingerprinterTask : IScheduledTask
// ===== Method 3: Full scan =====
// Compares all elements of the shortest fingerprint to the other fingerprint.
var limit = Math.Min(lhsPoints.Count, rhsPoints.Count);
var limit = Math.Min(lhsPoints.Length, rhsPoints.Length);
(lhsRanges, rhsRanges) = ShiftEpisodes(lhsPoints, rhsPoints, -1 * limit, limit);
if (lhsRanges.Count > 0)
@ -535,8 +535,8 @@ public class FingerprinterTask : IScheduledTask
/// <param name="rhsPoints">Right episode fingerprint points.</param>
/// <returns>List of shared TimeRanges between the left and right episodes.</returns>
private (List<TimeRange> Lhs, List<TimeRange> Rhs) SearchInvertedIndex(
ReadOnlyCollection<uint> lhsPoints,
ReadOnlyCollection<uint> rhsPoints)
uint[] lhsPoints,
uint[] rhsPoints)
{
var lhsRanges = new List<TimeRange>();
var rhsRanges = new List<TimeRange>();
@ -579,8 +579,8 @@ public class FingerprinterTask : IScheduledTask
/// <param name="lower">Lower end of the shift range.</param>
/// <param name="upper">Upper end of the shift range.</param>
private static (List<TimeRange> Lhs, List<TimeRange> Rhs) ShiftEpisodes(
ReadOnlyCollection<uint> lhs,
ReadOnlyCollection<uint> rhs,
uint[] lhs,
uint[] rhs,
int lower,
int upper)
{
@ -610,8 +610,8 @@ public class FingerprinterTask : IScheduledTask
/// <param name="rhs">Second fingerprint to compare.</param>
/// <param name="shiftAmount">Amount to shift one fingerprint by.</param>
private static (TimeRange Lhs, TimeRange Rhs) FindContiguous(
ReadOnlyCollection<uint> lhs,
ReadOnlyCollection<uint> rhs,
uint[] lhs,
uint[] rhs,
int shiftAmount)
{
var leftOffset = 0;
@ -630,7 +630,7 @@ public class FingerprinterTask : IScheduledTask
// Store similar times for both LHS and RHS.
var lhsTimes = new List<double>();
var rhsTimes = new List<double>();
var upperLimit = Math.Min(lhs.Count, rhs.Count) - Math.Abs(shiftAmount);
var upperLimit = Math.Min(lhs.Length, rhs.Length) - Math.Abs(shiftAmount);
// XOR all elements in LHS and RHS, using the shift amount from above.
for (var i = 0; i < upperLimit; i++)
@ -785,7 +785,7 @@ public class FingerprinterTask : IScheduledTask
// TODO: add limit and make it customizable
var count = maxBucket.Episodes.Count - 1;
var goodFingerprints = new List<ReadOnlyCollection<uint>>();
var goodFingerprints = new List<uint[]>();
foreach (var id in maxBucket.Episodes)
{
if (!_fingerprintCache.TryGetValue(id, out var fp))