From 3f48f5c42ce1a8ed074f96f43e0c51857b9d45f6 Mon Sep 17 00:00:00 2001 From: Matt Nadareski Date: Wed, 13 Mar 2024 01:22:59 -0400 Subject: [PATCH] Consolidate statistics into a single place again --- SabreTools.DatFiles/DatFile.cs | 2 +- SabreTools.DatFiles/DatStatistics.cs | 411 +++++++++++++++++ SabreTools.DatFiles/ItemDictionary.cs | 412 +----------------- SabreTools.DatFiles/ItemDictionaryDB.cs | 412 +----------------- SabreTools.DatTools/Rebuilder.cs | 4 +- SabreTools.DatTools/Splitter.cs | 2 +- SabreTools.DatTools/Statistics.cs | 30 +- SabreTools.DatTools/Writer.cs | 24 +- SabreTools.Reports/BaseReport.cs | 2 +- SabreTools.Reports/DatStatistics.cs | 30 -- SabreTools.Reports/Formats/Html.cs | 19 +- SabreTools.Reports/Formats/SeparatedValue.cs | 23 +- SabreTools.Reports/Formats/Textfile.cs | 23 +- .../DatFiles/ItemDictionaryTests.cs | 7 +- SabreTools.Test/DatTools/ParserTests.cs | 2 +- 15 files changed, 519 insertions(+), 884 deletions(-) create mode 100644 SabreTools.DatFiles/DatStatistics.cs delete mode 100644 SabreTools.Reports/DatStatistics.cs diff --git a/SabreTools.DatFiles/DatFile.cs b/SabreTools.DatFiles/DatFile.cs index ebe40453..c171025d 100644 --- a/SabreTools.DatFiles/DatFile.cs +++ b/SabreTools.DatFiles/DatFile.cs @@ -296,7 +296,7 @@ namespace SabreTools.DatFiles if (statsOnly) { Items.EnsureKey(key); - Items.AddItemStatistics(item); + Items.DatStatistics.AddItemStatistics(item); } else { diff --git a/SabreTools.DatFiles/DatStatistics.cs b/SabreTools.DatFiles/DatStatistics.cs new file mode 100644 index 00000000..5c7a0c88 --- /dev/null +++ b/SabreTools.DatFiles/DatStatistics.cs @@ -0,0 +1,411 @@ +using System.Collections.Generic; +using SabreTools.Core.Tools; +using SabreTools.DatItems; +using SabreTools.DatItems.Formats; +using SabreTools.Hashing; + +namespace SabreTools.DatFiles +{ + /// + /// Statistics wrapper for outputting + /// + public class DatStatistics + { + #region Private instance variables + + /// + /// Lock for statistics calculation + /// + private readonly object statsLock = new(); + + #endregion + + #region Fields + + /// + /// Overall item count + /// + public long TotalCount { get; private set; } = 0; + + /// + /// Number of items for each item type + /// + public Dictionary ItemCounts { get; private set; } = []; + + /// + /// Number of machines + /// + /// Special count only used by statistics output + public long GameCount { get; set; } = 0; + + /// + /// Total uncompressed size + /// + public long TotalSize { get; private set; } = 0; + + /// + /// Number of items for each hash type + /// + public Dictionary HashCounts { get; private set; } = []; + + /// + /// Number of items for each item status + /// + public Dictionary StatusCounts { get; private set; } = []; + + /// + /// Number of items with the remove flag + /// + public long RemovedCount { get; private set; } = 0; + + /// + /// Name to display on output + /// + public string? DisplayName { get; set; } + + /// + /// Total machine count to use on output + /// + public long MachineCount { get; set; } = 0; + + /// + /// Determines if statistics are for a directory or not + /// + public bool IsDirectory { get; set; } = false; + + #endregion + + #region Accessors + + /// + /// Add to the statistics given a DatItem + /// + /// Item to add info from + public void AddItemStatistics(DatItem item) + { + lock (statsLock) + { + // No matter what the item is, we increment the count + TotalCount++; + + // Increment removal count + if (item.GetBoolFieldValue(DatItem.RemoveKey) == true) + RemovedCount++; + + // Increment the item count for the type + AddItemCount(item.GetStringFieldValue(Models.Metadata.DatItem.TypeKey).AsEnumValue()); + + // Some item types require special processing + switch (item) + { + case Disk disk: + if (disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() != ItemStatus.Nodump) + { + AddHashCount(HashType.MD5, string.IsNullOrEmpty(disk.GetStringFieldValue(Models.Metadata.Disk.MD5Key)) ? 0 : 1); + AddHashCount(HashType.SHA1, string.IsNullOrEmpty(disk.GetStringFieldValue(Models.Metadata.Disk.SHA1Key)) ? 0 : 1); + } + + AddStatusCount(ItemStatus.BadDump, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.BadDump ? 1 : 0); + AddStatusCount(ItemStatus.Good, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Good ? 1 : 0); + AddStatusCount(ItemStatus.Nodump, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Nodump ? 1 : 0); + AddStatusCount(ItemStatus.Verified, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Verified ? 1 : 0); + break; + case Media media: + AddHashCount(HashType.MD5, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.MD5Key)) ? 0 : 1); + AddHashCount(HashType.SHA1, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SHA1Key)) ? 0 : 1); + AddHashCount(HashType.SHA256, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SHA256Key)) ? 0 : 1); + AddHashCount(HashType.SpamSum, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SpamSumKey)) ? 0 : 1); + break; + case Rom rom: + if (rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() != ItemStatus.Nodump) + { + TotalSize += rom.GetInt64FieldValue(Models.Metadata.Rom.SizeKey) ?? 0; + AddHashCount(HashType.CRC32, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.CRCKey)) ? 0 : 1); + AddHashCount(HashType.MD5, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.MD5Key)) ? 0 : 1); + AddHashCount(HashType.SHA1, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA1Key)) ? 0 : 1); + AddHashCount(HashType.SHA256, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA256Key)) ? 0 : 1); + AddHashCount(HashType.SHA384, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA384Key)) ? 0 : 1); + AddHashCount(HashType.SHA512, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA512Key)) ? 0 : 1); + AddHashCount(HashType.SpamSum, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SpamSumKey)) ? 0 : 1); + } + + AddStatusCount(ItemStatus.BadDump, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.BadDump ? 1 : 0); + AddStatusCount(ItemStatus.Good, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Good ? 1 : 0); + AddStatusCount(ItemStatus.Nodump, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Nodump ? 1 : 0); + AddStatusCount(ItemStatus.Verified, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Verified ? 1 : 0); + break; + } + } + } + + /// + /// Add statistics from another DatStatistics object + /// + /// DatStatistics object to add from + public void AddStatistics(DatStatistics stats) + { + TotalCount += stats.TotalCount; + + // Loop through and add stats for all items + foreach (var itemCountKvp in stats.ItemCounts) + { + AddItemCount(itemCountKvp.Key, itemCountKvp.Value); + } + + GameCount += stats.GameCount; + + TotalSize += stats.TotalSize; + + // Individual hash counts + foreach (var hashCountKvp in stats.HashCounts) + { + AddHashCount(hashCountKvp.Key, hashCountKvp.Value); + } + + // Individual status counts + foreach (var statusCountKvp in stats.StatusCounts) + { + AddStatusCount(statusCountKvp.Key, statusCountKvp.Value); + } + + RemovedCount += stats.RemovedCount; + } + + /// + /// Get the item count for a given hash type, defaulting to 0 if it does not exist + /// + /// Hash type to retrieve + /// The number of items with that hash, if it exists + public long GetHashCount(HashType hashType) + { + lock (HashCounts) + { + if (!HashCounts.ContainsKey(hashType)) + return 0; + + return HashCounts[hashType]; + } + } + + /// + /// Get the item count for a given item type, defaulting to 0 if it does not exist + /// + /// Item type to retrieve + /// The number of items of that type, if it exists + public long GetItemCount(ItemType itemType) + { + lock (ItemCounts) + { + if (!ItemCounts.ContainsKey(itemType)) + return 0; + + return ItemCounts[itemType]; + } + } + + /// + /// Get the item count for a given item status, defaulting to 0 if it does not exist + /// + /// Item status to retrieve + /// The number of items of that type, if it exists + public long GetStatusCount(ItemStatus itemStatus) + { + lock (StatusCounts) + { + if (!StatusCounts.ContainsKey(itemStatus)) + return 0; + + return StatusCounts[itemStatus]; + } + } + + /// + /// Increment the hash count for a given hash type + /// + /// Hash type to increment + /// Amount to increment by, defaults to 1 + private void AddHashCount(HashType hashType, long interval = 1) + { + lock (HashCounts) + { + if (!HashCounts.ContainsKey(hashType)) + HashCounts[hashType] = 0; + + HashCounts[hashType] += interval; + if (HashCounts[hashType] < 0) + HashCounts[hashType] = 0; + } + } + + /// + /// Increment the item count for a given item type + /// + /// Item type to increment + /// Amount to increment by, defaults to 1 + private void AddItemCount(ItemType itemType, long interval = 1) + { + lock (ItemCounts) + { + if (!ItemCounts.ContainsKey(itemType)) + ItemCounts[itemType] = 0; + + ItemCounts[itemType] += interval; + if (ItemCounts[itemType] < 0) + ItemCounts[itemType] = 0; + } + } + + /// + /// Increment the item count for a given item status + /// + /// Item type to increment + /// Amount to increment by, defaults to 1 + private void AddStatusCount(ItemStatus itemStatus, long interval = 1) + { + lock (StatusCounts) + { + if (!StatusCounts.ContainsKey(itemStatus)) + StatusCounts[itemStatus] = 0; + + StatusCounts[itemStatus] += interval; + if (StatusCounts[itemStatus] < 0) + StatusCounts[itemStatus] = 0; + } + } + + /// + /// Remove from the statistics given a DatItem + /// + /// Item to remove info for + public void RemoveItemStatistics(DatItem item) + { + // If we have a null item, we can't do anything + if (item == null) + return; + + lock (statsLock) + { + // No matter what the item is, we decrease the count + TotalCount--; + + // Decrement removal count + if (item.GetBoolFieldValue(DatItem.RemoveKey) == true) + RemovedCount--; + + // Decrement the item count for the type + RemoveItemCount(item.GetStringFieldValue(Models.Metadata.DatItem.TypeKey).AsEnumValue()); + + // Some item types require special processing + switch (item) + { + case Disk disk: + if (disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() != ItemStatus.Nodump) + { + RemoveHashCount(HashType.MD5, string.IsNullOrEmpty(disk.GetStringFieldValue(Models.Metadata.Disk.MD5Key)) ? 0 : 1); + RemoveHashCount(HashType.SHA1, string.IsNullOrEmpty(disk.GetStringFieldValue(Models.Metadata.Disk.SHA1Key)) ? 0 : 1); + } + + RemoveStatusCount(ItemStatus.BadDump, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.BadDump ? 1 : 0); + RemoveStatusCount(ItemStatus.Good, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Good ? 1 : 0); + RemoveStatusCount(ItemStatus.Nodump, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Nodump ? 1 : 0); + RemoveStatusCount(ItemStatus.Verified, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Verified ? 1 : 0); + break; + case Media media: + RemoveHashCount(HashType.MD5, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.MD5Key)) ? 0 : 1); + RemoveHashCount(HashType.SHA1, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SHA1Key)) ? 0 : 1); + RemoveHashCount(HashType.SHA256, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SHA256Key)) ? 0 : 1); + RemoveHashCount(HashType.SpamSum, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SpamSumKey)) ? 0 : 1); + break; + case Rom rom: + if (rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() != ItemStatus.Nodump) + { + TotalSize -= rom.GetInt64FieldValue(Models.Metadata.Rom.SizeKey) ?? 0; + RemoveHashCount(HashType.CRC32, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.CRCKey)) ? 0 : 1); + RemoveHashCount(HashType.MD5, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.MD5Key)) ? 0 : 1); + RemoveHashCount(HashType.SHA1, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA1Key)) ? 0 : 1); + RemoveHashCount(HashType.SHA256, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA256Key)) ? 0 : 1); + RemoveHashCount(HashType.SHA384, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA384Key)) ? 0 : 1); + RemoveHashCount(HashType.SHA512, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA512Key)) ? 0 : 1); + RemoveHashCount(HashType.SpamSum, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SpamSumKey)) ? 0 : 1); + } + + RemoveStatusCount(ItemStatus.BadDump, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.BadDump ? 1 : 0); + RemoveStatusCount(ItemStatus.Good, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Good ? 1 : 0); + RemoveStatusCount(ItemStatus.Nodump, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Nodump ? 1 : 0); + RemoveStatusCount(ItemStatus.Verified, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Verified ? 1 : 0); + break; + } + } + } + + /// + /// Reset all statistics + /// + public void ResetStatistics() + { + TotalCount = 0; + ItemCounts = []; + GameCount = 0; + TotalSize = 0; + HashCounts = []; + StatusCounts = []; + RemovedCount = 0; + } + + /// + /// Decrement the hash count for a given hash type + /// + /// Hash type to increment + /// Amount to increment by, defaults to 1 + private void RemoveHashCount(HashType hashType, long interval = 1) + { + lock (HashCounts) + { + if (!HashCounts.ContainsKey(hashType)) + return; + + HashCounts[hashType] -= interval; + if (HashCounts[hashType] < 0) + HashCounts[hashType] = 0; + } + } + + /// + /// Decrement the item count for a given item type + /// + /// Item type to decrement + /// Amount to increment by, defaults to 1 + private void RemoveItemCount(ItemType itemType, long interval = 1) + { + lock (ItemCounts) + { + if (!ItemCounts.ContainsKey(itemType)) + return; + + ItemCounts[itemType] -= interval; + if (ItemCounts[itemType] < 0) + ItemCounts[itemType] = 0; + } + } + + /// + /// Decrement the item count for a given item status + /// + /// Item type to decrement + /// Amount to increment by, defaults to 1 + private void RemoveStatusCount(ItemStatus itemStatus, long interval = 1) + { + lock (StatusCounts) + { + if (!StatusCounts.ContainsKey(itemStatus)) + return; + + StatusCounts[itemStatus] -= interval; + if (StatusCounts[itemStatus] < 0) + StatusCounts[itemStatus] = 0; + } + } + + #endregion + } +} diff --git a/SabreTools.DatFiles/ItemDictionary.cs b/SabreTools.DatFiles/ItemDictionary.cs index fca04aa5..3bcc215f 100644 --- a/SabreTools.DatFiles/ItemDictionary.cs +++ b/SabreTools.DatFiles/ItemDictionary.cs @@ -10,7 +10,6 @@ using System.Threading.Tasks; using System.Xml.Serialization; using Newtonsoft.Json; using SabreTools.Core; -using SabreTools.Core.Tools; using SabreTools.DatItems; using SabreTools.DatItems.Formats; using SabreTools.Hashing; @@ -50,11 +49,6 @@ namespace SabreTools.DatFiles private readonly Dictionary?> items; #endif - /// - /// Lock for statistics calculation - /// - private readonly object statsLock = new(); - /// /// Logging object /// @@ -96,47 +90,10 @@ namespace SabreTools.DatFiles #region Statistics /// - /// Overall item count + /// DAT statistics /// [JsonIgnore, XmlIgnore] - public long TotalCount { get; private set; } = 0; - - /// - /// Number of items for each item type - /// - [JsonIgnore, XmlIgnore] - public Dictionary ItemCounts { get; private set; } = []; - - /// - /// Number of machines - /// - /// Special count only used by statistics output - [JsonIgnore, XmlIgnore] - public long GameCount { get; set; } = 0; - - /// - /// Total uncompressed size - /// - [JsonIgnore, XmlIgnore] - public long TotalSize { get; private set; } = 0; - - /// - /// Number of items for each hash type - /// - [JsonIgnore, XmlIgnore] - public Dictionary HashCounts { get; private set; } = []; - - /// - /// Number of items for each item status - /// - [JsonIgnore, XmlIgnore] - public Dictionary StatusCounts { get; private set; } = []; - - /// - /// Number of items with the remove flag - /// - [JsonIgnore, XmlIgnore] - public long RemovedCount { get; private set; } = 0; + public DatStatistics DatStatistics { get; } = new DatStatistics(); #endregion @@ -193,7 +150,7 @@ namespace SabreTools.DatFiles items[key]!.Add(value); // Now update the statistics - AddItemStatistics(value); + DatStatistics.AddItemStatistics(value); } } @@ -207,67 +164,6 @@ namespace SabreTools.DatFiles AddRange(key, value); } - /// - /// Add to the statistics given a DatItem - /// - /// Item to add info from - public void AddItemStatistics(DatItem item) - { - lock (statsLock) - { - // No matter what the item is, we increment the count - TotalCount++; - - // Increment removal count - if (item.GetBoolFieldValue(DatItem.RemoveKey) == true) - RemovedCount++; - - // Increment the item count for the type - AddItemCount(item.GetStringFieldValue(Models.Metadata.DatItem.TypeKey).AsEnumValue()); - - // Some item types require special processing - switch (item) - { - case Disk disk: - if (disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() != ItemStatus.Nodump) - { - AddHashCount(HashType.MD5, string.IsNullOrEmpty(disk.GetStringFieldValue(Models.Metadata.Disk.MD5Key)) ? 0 : 1); - AddHashCount(HashType.SHA1, string.IsNullOrEmpty(disk.GetStringFieldValue(Models.Metadata.Disk.SHA1Key)) ? 0 : 1); - } - - AddStatusCount(ItemStatus.BadDump, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.BadDump ? 1 : 0); - AddStatusCount(ItemStatus.Good, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Good ? 1 : 0); - AddStatusCount(ItemStatus.Nodump, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Nodump ? 1 : 0); - AddStatusCount(ItemStatus.Verified, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Verified ? 1 : 0); - break; - case Media media: - AddHashCount(HashType.MD5, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.MD5Key)) ? 0 : 1); - AddHashCount(HashType.SHA1, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SHA1Key)) ? 0 : 1); - AddHashCount(HashType.SHA256, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SHA256Key)) ? 0 : 1); - AddHashCount(HashType.SpamSum, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SpamSumKey)) ? 0 : 1); - break; - case Rom rom: - if (rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() != ItemStatus.Nodump) - { - TotalSize += rom.GetInt64FieldValue(Models.Metadata.Rom.SizeKey) ?? 0; - AddHashCount(HashType.CRC32, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.CRCKey)) ? 0 : 1); - AddHashCount(HashType.MD5, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.MD5Key)) ? 0 : 1); - AddHashCount(HashType.SHA1, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA1Key)) ? 0 : 1); - AddHashCount(HashType.SHA256, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA256Key)) ? 0 : 1); - AddHashCount(HashType.SHA384, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA384Key)) ? 0 : 1); - AddHashCount(HashType.SHA512, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA512Key)) ? 0 : 1); - AddHashCount(HashType.SpamSum, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SpamSumKey)) ? 0 : 1); - } - - AddStatusCount(ItemStatus.BadDump, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.BadDump ? 1 : 0); - AddStatusCount(ItemStatus.Good, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Good ? 1 : 0); - AddStatusCount(ItemStatus.Nodump, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Nodump ? 1 : 0); - AddStatusCount(ItemStatus.Verified, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Verified ? 1 : 0); - break; - } - } - } - /// /// Add a range of values to the file dictionary /// @@ -291,44 +187,11 @@ namespace SabreTools.DatFiles // Now update the statistics foreach (DatItem item in value) { - AddItemStatistics(item); + DatStatistics.AddItemStatistics(item); } } } - /// - /// Add statistics from another DatStats object - /// - /// DatStats object to add from - public void AddStatistics(ItemDictionary stats) - { - TotalCount += stats.Count; - - // Loop through and add stats for all items - foreach (var itemCountKvp in stats.ItemCounts) - { - AddItemCount(itemCountKvp.Key, itemCountKvp.Value); - } - - GameCount += stats.GameCount; - - TotalSize += stats.TotalSize; - - // Individual hash counts - foreach (var hashCountKvp in stats.HashCounts) - { - AddHashCount(hashCountKvp.Key, hashCountKvp.Value); - } - - // Individual status counts - foreach (var statusCountKvp in stats.StatusCounts) - { - AddStatusCount(statusCountKvp.Key, statusCountKvp.Value); - } - - RemovedCount += stats.RemovedCount; - } - /// /// Get if the file dictionary contains the key /// @@ -421,7 +284,7 @@ namespace SabreTools.DatFiles // Remove the statistics first foreach (DatItem item in items[key]!) { - RemoveItemStatistics(item); + DatStatistics.RemoveItemStatistics(item); } // Remove the key from the dictionary @@ -448,7 +311,7 @@ namespace SabreTools.DatFiles return false; // Remove the statistics first - RemoveItemStatistics(value); + DatStatistics.RemoveItemStatistics(value); return items[key]!.Remove(value); } @@ -467,7 +330,7 @@ namespace SabreTools.DatFiles // Remove the statistics first foreach (DatItem item in items[key]!) { - RemoveItemStatistics(item); + DatStatistics.RemoveItemStatistics(item); } // Remove the key from the dictionary @@ -484,227 +347,6 @@ namespace SabreTools.DatFiles bucketedBy = newBucket; } - /// - /// Remove from the statistics given a DatItem - /// - /// Item to remove info for - public void RemoveItemStatistics(DatItem item) - { - // If we have a null item, we can't do anything - if (item == null) - return; - - lock (statsLock) - { - // No matter what the item is, we decrease the count - TotalCount--; - - // Decrement removal count - if (item.GetBoolFieldValue(DatItem.RemoveKey) == true) - RemovedCount--; - - // Decrement the item count for the type - RemoveItemCount(item.GetStringFieldValue(Models.Metadata.DatItem.TypeKey).AsEnumValue()); - - // Some item types require special processing - switch (item) - { - case Disk disk: - if (disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() != ItemStatus.Nodump) - { - RemoveHashCount(HashType.MD5, string.IsNullOrEmpty(disk.GetStringFieldValue(Models.Metadata.Disk.MD5Key)) ? 0 : 1); - RemoveHashCount(HashType.SHA1, string.IsNullOrEmpty(disk.GetStringFieldValue(Models.Metadata.Disk.SHA1Key)) ? 0 : 1); - } - - RemoveStatusCount(ItemStatus.BadDump, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.BadDump ? 1 : 0); - RemoveStatusCount(ItemStatus.Good, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Good ? 1 : 0); - RemoveStatusCount(ItemStatus.Nodump, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Nodump ? 1 : 0); - RemoveStatusCount(ItemStatus.Verified, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Verified ? 1 : 0); - break; - case Media media: - RemoveHashCount(HashType.MD5, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.MD5Key)) ? 0 : 1); - RemoveHashCount(HashType.SHA1, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SHA1Key)) ? 0 : 1); - RemoveHashCount(HashType.SHA256, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SHA256Key)) ? 0 : 1); - RemoveHashCount(HashType.SpamSum, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SpamSumKey)) ? 0 : 1); - break; - case Rom rom: - if (rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() != ItemStatus.Nodump) - { - TotalSize -= rom.GetInt64FieldValue(Models.Metadata.Rom.SizeKey) ?? 0; - RemoveHashCount(HashType.CRC32, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.CRCKey)) ? 0 : 1); - RemoveHashCount(HashType.MD5, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.MD5Key)) ? 0 : 1); - RemoveHashCount(HashType.SHA1, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA1Key)) ? 0 : 1); - RemoveHashCount(HashType.SHA256, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA256Key)) ? 0 : 1); - RemoveHashCount(HashType.SHA384, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA384Key)) ? 0 : 1); - RemoveHashCount(HashType.SHA512, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA512Key)) ? 0 : 1); - RemoveHashCount(HashType.SpamSum, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SpamSumKey)) ? 0 : 1); - } - - RemoveStatusCount(ItemStatus.BadDump, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.BadDump ? 1 : 0); - RemoveStatusCount(ItemStatus.Good, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Good ? 1 : 0); - RemoveStatusCount(ItemStatus.Nodump, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Nodump ? 1 : 0); - RemoveStatusCount(ItemStatus.Verified, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Verified ? 1 : 0); - break; - } - } - } - - /// - /// Get the item count for a given hash type, defaulting to 0 if it does not exist - /// - /// Hash type to retrieve - /// The number of items with that hash, if it exists - public long GetHashCount(HashType hashType) - { - lock (HashCounts) - { - if (!HashCounts.ContainsKey(hashType)) - return 0; - - return HashCounts[hashType]; - } - } - - /// - /// Get the item count for a given item type, defaulting to 0 if it does not exist - /// - /// Item type to retrieve - /// The number of items of that type, if it exists - public long GetItemCount(ItemType itemType) - { - lock (ItemCounts) - { - if (!ItemCounts.ContainsKey(itemType)) - return 0; - - return ItemCounts[itemType]; - } - } - - /// - /// Get the item count for a given item status, defaulting to 0 if it does not exist - /// - /// Item status to retrieve - /// The number of items of that type, if it exists - public long GetStatusCount(ItemStatus itemStatus) - { - lock (StatusCounts) - { - if (!StatusCounts.ContainsKey(itemStatus)) - return 0; - - return StatusCounts[itemStatus]; - } - } - - /// - /// Increment the hash count for a given hash type - /// - /// Hash type to increment - /// Amount to increment by, defaults to 1 - private void AddHashCount(HashType hashType, long interval = 1) - { - lock (HashCounts) - { - if (!HashCounts.ContainsKey(hashType)) - HashCounts[hashType] = 0; - - HashCounts[hashType] += interval; - if (HashCounts[hashType] < 0) - HashCounts[hashType] = 0; - } - } - - /// - /// Decrement the hash count for a given hash type - /// - /// Hash type to increment - /// Amount to increment by, defaults to 1 - private void RemoveHashCount(HashType hashType, long interval = 1) - { - lock (HashCounts) - { - if (!HashCounts.ContainsKey(hashType)) - return; - - HashCounts[hashType] -= interval; - if (HashCounts[hashType] < 0) - HashCounts[hashType] = 0; - } - } - - /// - /// Increment the item count for a given item type - /// - /// Item type to increment - /// Amount to increment by, defaults to 1 - private void AddItemCount(ItemType itemType, long interval = 1) - { - lock (ItemCounts) - { - if (!ItemCounts.ContainsKey(itemType)) - ItemCounts[itemType] = 0; - - ItemCounts[itemType] += interval; - if (ItemCounts[itemType] < 0) - ItemCounts[itemType] = 0; - } - } - - /// - /// Decrement the item count for a given item type - /// - /// Item type to decrement - /// Amount to increment by, defaults to 1 - private void RemoveItemCount(ItemType itemType, long interval = 1) - { - lock (ItemCounts) - { - if (!ItemCounts.ContainsKey(itemType)) - return; - - ItemCounts[itemType] -= interval; - if (ItemCounts[itemType] < 0) - ItemCounts[itemType] = 0; - } - } - - /// - /// Increment the item count for a given item status - /// - /// Item type to increment - /// Amount to increment by, defaults to 1 - private void AddStatusCount(ItemStatus itemStatus, long interval = 1) - { - lock (StatusCounts) - { - if (!StatusCounts.ContainsKey(itemStatus)) - StatusCounts[itemStatus] = 0; - - StatusCounts[itemStatus] += interval; - if (StatusCounts[itemStatus] < 0) - StatusCounts[itemStatus] = 0; - } - } - - /// - /// Decrement the item count for a given item status - /// - /// Item type to decrement - /// Amount to increment by, defaults to 1 - private void RemoveStatusCount(ItemStatus itemStatus, long interval = 1) - { - lock (StatusCounts) - { - if (!StatusCounts.ContainsKey(itemStatus)) - return; - - StatusCounts[itemStatus] -= interval; - if (StatusCounts[itemStatus] < 0) - StatusCounts[itemStatus] = 0; - } - } - #endregion #region Constructors @@ -925,7 +567,7 @@ namespace SabreTools.DatFiles ConcurrentList output = []; // Check for an empty rom list first - if (TotalCount == 0) + if (DatStatistics.TotalCount == 0) return output; // We want to get the proper key for the DatItem @@ -975,7 +617,7 @@ namespace SabreTools.DatFiles public bool HasDuplicates(DatItem datItem, bool sorted = false) { // Check for an empty rom list first - if (TotalCount == 0) + if (DatStatistics.TotalCount == 0) return false; // We want to get the proper key for the DatItem @@ -996,7 +638,7 @@ namespace SabreTools.DatFiles public void RecalculateStats() { // Wipe out any stats already there - ResetStatistics(); + DatStatistics.ResetStatistics(); // If we have a blank Dat in any way, return if (items == null) @@ -1011,54 +653,40 @@ namespace SabreTools.DatFiles foreach (DatItem item in datItems) { - AddItemStatistics(item); + DatStatistics.AddItemStatistics(item); } } } - /// - /// Reset all statistics - /// - public void ResetStatistics() - { - TotalCount = 0; - ItemCounts = []; - GameCount = 0; - TotalSize = 0; - HashCounts = []; - StatusCounts = []; - RemovedCount = 0; - } - /// /// Get the highest-order Field value that represents the statistics /// private ItemKey GetBestAvailable() { // Get the required counts - long diskCount = GetItemCount(ItemType.Disk); - long mediaCount = GetItemCount(ItemType.Media); - long romCount = GetItemCount(ItemType.Rom); - long nodumpCount = GetStatusCount(ItemStatus.Nodump); + long diskCount = DatStatistics.GetItemCount(ItemType.Disk); + long mediaCount = DatStatistics.GetItemCount(ItemType.Media); + long romCount = DatStatistics.GetItemCount(ItemType.Rom); + long nodumpCount = DatStatistics.GetStatusCount(ItemStatus.Nodump); // If all items are supposed to have a SHA-512, we bucket by that - if (diskCount + mediaCount + romCount - nodumpCount == GetHashCount(HashType.SHA512)) + if (diskCount + mediaCount + romCount - nodumpCount == DatStatistics.GetHashCount(HashType.SHA512)) return ItemKey.SHA512; // If all items are supposed to have a SHA-384, we bucket by that - else if (diskCount + mediaCount + romCount - nodumpCount == GetHashCount(HashType.SHA384)) + else if (diskCount + mediaCount + romCount - nodumpCount == DatStatistics.GetHashCount(HashType.SHA384)) return ItemKey.SHA384; // If all items are supposed to have a SHA-256, we bucket by that - else if (diskCount + mediaCount + romCount - nodumpCount == GetHashCount(HashType.SHA256)) + else if (diskCount + mediaCount + romCount - nodumpCount == DatStatistics.GetHashCount(HashType.SHA256)) return ItemKey.SHA256; // If all items are supposed to have a SHA-1, we bucket by that - else if (diskCount + mediaCount + romCount - nodumpCount == GetHashCount(HashType.SHA1)) + else if (diskCount + mediaCount + romCount - nodumpCount == DatStatistics.GetHashCount(HashType.SHA1)) return ItemKey.SHA1; // If all items are supposed to have a MD5, we bucket by that - else if (diskCount + mediaCount + romCount - nodumpCount == GetHashCount(HashType.MD5)) + else if (diskCount + mediaCount + romCount - nodumpCount == DatStatistics.GetHashCount(HashType.MD5)) return ItemKey.MD5; // Otherwise, we bucket by CRC diff --git a/SabreTools.DatFiles/ItemDictionaryDB.cs b/SabreTools.DatFiles/ItemDictionaryDB.cs index 6d9d1433..9aa5f3fd 100644 --- a/SabreTools.DatFiles/ItemDictionaryDB.cs +++ b/SabreTools.DatFiles/ItemDictionaryDB.cs @@ -10,7 +10,6 @@ using System.Threading.Tasks; using System.Xml.Serialization; using Newtonsoft.Json; using SabreTools.Core; -using SabreTools.Core.Tools; using SabreTools.DatItems; using SabreTools.DatItems.Formats; using SabreTools.Hashing; @@ -55,11 +54,6 @@ namespace SabreTools.DatFiles private readonly Dictionary machines; #endif - /// - /// Lock for statistics calculation - /// - private readonly object statsLock = new(); - /// /// Logging object /// @@ -101,47 +95,10 @@ namespace SabreTools.DatFiles #region Statistics /// - /// Overall item count + /// DAT statistics /// [JsonIgnore, XmlIgnore] - public long TotalCount { get; private set; } = 0; - - /// - /// Number of items for each item type - /// - [JsonIgnore, XmlIgnore] - public Dictionary ItemCounts { get; private set; } = []; - - /// - /// Number of machines - /// - /// Special count only used by statistics output - [JsonIgnore, XmlIgnore] - public long GameCount { get; set; } = 0; - - /// - /// Total uncompressed size - /// - [JsonIgnore, XmlIgnore] - public long TotalSize { get; private set; } = 0; - - /// - /// Number of items for each hash type - /// - [JsonIgnore, XmlIgnore] - public Dictionary HashCounts { get; private set; } = []; - - /// - /// Number of items for each item status - /// - [JsonIgnore, XmlIgnore] - public Dictionary StatusCounts { get; private set; } = []; - - /// - /// Number of items with the remove flag - /// - [JsonIgnore, XmlIgnore] - public long RemovedCount { get; private set; } = 0; + public DatStatistics DatStatistics { get; } = new DatStatistics(); #endregion @@ -198,7 +155,7 @@ namespace SabreTools.DatFiles items[key]!.Add(value); // Now update the statistics - AddItemStatistics(value); + DatStatistics.AddItemStatistics(value); } } @@ -212,67 +169,6 @@ namespace SabreTools.DatFiles AddRange(key, value); } - /// - /// Add to the statistics given a DatItem - /// - /// Item to add info from - public void AddItemStatistics(DatItem item) - { - lock (statsLock) - { - // No matter what the item is, we increment the count - TotalCount++; - - // Increment removal count - if (item.GetBoolFieldValue(DatItem.RemoveKey) == true) - RemovedCount++; - - // Increment the item count for the type - AddItemCount(item.GetStringFieldValue(Models.Metadata.DatItem.TypeKey).AsEnumValue()); - - // Some item types require special processing - switch (item) - { - case Disk disk: - if (disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() != ItemStatus.Nodump) - { - AddHashCount(HashType.MD5, string.IsNullOrEmpty(disk.GetStringFieldValue(Models.Metadata.Disk.MD5Key)) ? 0 : 1); - AddHashCount(HashType.SHA1, string.IsNullOrEmpty(disk.GetStringFieldValue(Models.Metadata.Disk.SHA1Key)) ? 0 : 1); - } - - AddStatusCount(ItemStatus.BadDump, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.BadDump ? 1 : 0); - AddStatusCount(ItemStatus.Good, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Good ? 1 : 0); - AddStatusCount(ItemStatus.Nodump, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Nodump ? 1 : 0); - AddStatusCount(ItemStatus.Verified, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Verified ? 1 : 0); - break; - case Media media: - AddHashCount(HashType.MD5, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.MD5Key)) ? 0 : 1); - AddHashCount(HashType.SHA1, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SHA1Key)) ? 0 : 1); - AddHashCount(HashType.SHA256, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SHA256Key)) ? 0 : 1); - AddHashCount(HashType.SpamSum, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SpamSumKey)) ? 0 : 1); - break; - case Rom rom: - if (rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() != ItemStatus.Nodump) - { - TotalSize += rom.GetInt64FieldValue(Models.Metadata.Rom.SizeKey) ?? 0; - AddHashCount(HashType.CRC32, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.CRCKey)) ? 0 : 1); - AddHashCount(HashType.MD5, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.MD5Key)) ? 0 : 1); - AddHashCount(HashType.SHA1, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA1Key)) ? 0 : 1); - AddHashCount(HashType.SHA256, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA256Key)) ? 0 : 1); - AddHashCount(HashType.SHA384, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA384Key)) ? 0 : 1); - AddHashCount(HashType.SHA512, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA512Key)) ? 0 : 1); - AddHashCount(HashType.SpamSum, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SpamSumKey)) ? 0 : 1); - } - - AddStatusCount(ItemStatus.BadDump, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.BadDump ? 1 : 0); - AddStatusCount(ItemStatus.Good, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Good ? 1 : 0); - AddStatusCount(ItemStatus.Nodump, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Nodump ? 1 : 0); - AddStatusCount(ItemStatus.Verified, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Verified ? 1 : 0); - break; - } - } - } - /// /// Add a range of values to the file dictionary /// @@ -296,44 +192,11 @@ namespace SabreTools.DatFiles // Now update the statistics foreach (DatItem item in value) { - AddItemStatistics(item); + DatStatistics.AddItemStatistics(item); } } } - /// - /// Add statistics from another DatStats object - /// - /// DatStats object to add from - public void AddStatistics(ItemDictionary stats) - { - TotalCount += stats.Count; - - // Loop through and add stats for all items - foreach (var itemCountKvp in stats.ItemCounts) - { - AddItemCount(itemCountKvp.Key, itemCountKvp.Value); - } - - GameCount += stats.GameCount; - - TotalSize += stats.TotalSize; - - // Individual hash counts - foreach (var hashCountKvp in stats.HashCounts) - { - AddHashCount(hashCountKvp.Key, hashCountKvp.Value); - } - - // Individual status counts - foreach (var statusCountKvp in stats.StatusCounts) - { - AddStatusCount(statusCountKvp.Key, statusCountKvp.Value); - } - - RemovedCount += stats.RemovedCount; - } - /// /// Get if the file dictionary contains the key /// @@ -426,7 +289,7 @@ namespace SabreTools.DatFiles // Remove the statistics first foreach (DatItem item in items[key]!) { - RemoveItemStatistics(item); + DatStatistics.RemoveItemStatistics(item); } // Remove the key from the dictionary @@ -453,7 +316,7 @@ namespace SabreTools.DatFiles return false; // Remove the statistics first - RemoveItemStatistics(value); + DatStatistics.RemoveItemStatistics(value); return items[key]!.Remove(value); } @@ -472,7 +335,7 @@ namespace SabreTools.DatFiles // Remove the statistics first foreach (DatItem item in items[key]!) { - RemoveItemStatistics(item); + DatStatistics.RemoveItemStatistics(item); } // Remove the key from the dictionary @@ -489,227 +352,6 @@ namespace SabreTools.DatFiles bucketedBy = newBucket; } - /// - /// Remove from the statistics given a DatItem - /// - /// Item to remove info for - public void RemoveItemStatistics(DatItem item) - { - // If we have a null item, we can't do anything - if (item == null) - return; - - lock (statsLock) - { - // No matter what the item is, we decrease the count - TotalCount--; - - // Decrement removal count - if (item.GetBoolFieldValue(DatItem.RemoveKey) == true) - RemovedCount--; - - // Decrement the item count for the type - RemoveItemCount(item.GetStringFieldValue(Models.Metadata.DatItem.TypeKey).AsEnumValue()); - - // Some item types require special processing - switch (item) - { - case Disk disk: - if (disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() != ItemStatus.Nodump) - { - RemoveHashCount(HashType.MD5, string.IsNullOrEmpty(disk.GetStringFieldValue(Models.Metadata.Disk.MD5Key)) ? 0 : 1); - RemoveHashCount(HashType.SHA1, string.IsNullOrEmpty(disk.GetStringFieldValue(Models.Metadata.Disk.SHA1Key)) ? 0 : 1); - } - - RemoveStatusCount(ItemStatus.BadDump, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.BadDump ? 1 : 0); - RemoveStatusCount(ItemStatus.Good, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Good ? 1 : 0); - RemoveStatusCount(ItemStatus.Nodump, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Nodump ? 1 : 0); - RemoveStatusCount(ItemStatus.Verified, disk.GetStringFieldValue(Models.Metadata.Disk.StatusKey).AsEnumValue() == ItemStatus.Verified ? 1 : 0); - break; - case Media media: - RemoveHashCount(HashType.MD5, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.MD5Key)) ? 0 : 1); - RemoveHashCount(HashType.SHA1, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SHA1Key)) ? 0 : 1); - RemoveHashCount(HashType.SHA256, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SHA256Key)) ? 0 : 1); - RemoveHashCount(HashType.SpamSum, string.IsNullOrEmpty(media.GetStringFieldValue(Models.Metadata.Media.SpamSumKey)) ? 0 : 1); - break; - case Rom rom: - if (rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() != ItemStatus.Nodump) - { - TotalSize -= rom.GetInt64FieldValue(Models.Metadata.Rom.SizeKey) ?? 0; - RemoveHashCount(HashType.CRC32, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.CRCKey)) ? 0 : 1); - RemoveHashCount(HashType.MD5, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.MD5Key)) ? 0 : 1); - RemoveHashCount(HashType.SHA1, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA1Key)) ? 0 : 1); - RemoveHashCount(HashType.SHA256, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA256Key)) ? 0 : 1); - RemoveHashCount(HashType.SHA384, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA384Key)) ? 0 : 1); - RemoveHashCount(HashType.SHA512, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SHA512Key)) ? 0 : 1); - RemoveHashCount(HashType.SpamSum, string.IsNullOrEmpty(rom.GetStringFieldValue(Models.Metadata.Rom.SpamSumKey)) ? 0 : 1); - } - - RemoveStatusCount(ItemStatus.BadDump, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.BadDump ? 1 : 0); - RemoveStatusCount(ItemStatus.Good, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Good ? 1 : 0); - RemoveStatusCount(ItemStatus.Nodump, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Nodump ? 1 : 0); - RemoveStatusCount(ItemStatus.Verified, rom.GetStringFieldValue(Models.Metadata.Rom.StatusKey).AsEnumValue() == ItemStatus.Verified ? 1 : 0); - break; - } - } - } - - /// - /// Get the item count for a given hash type, defaulting to 0 if it does not exist - /// - /// Hash type to retrieve - /// The number of items with that hash, if it exists - public long GetHashCount(HashType hashType) - { - lock (HashCounts) - { - if (!HashCounts.ContainsKey(hashType)) - return 0; - - return HashCounts[hashType]; - } - } - - /// - /// Get the item count for a given item type, defaulting to 0 if it does not exist - /// - /// Item type to retrieve - /// The number of items of that type, if it exists - public long GetItemCount(ItemType itemType) - { - lock (ItemCounts) - { - if (!ItemCounts.ContainsKey(itemType)) - return 0; - - return ItemCounts[itemType]; - } - } - - /// - /// Get the item count for a given item status, defaulting to 0 if it does not exist - /// - /// Item status to retrieve - /// The number of items of that type, if it exists - public long GetStatusCount(ItemStatus itemStatus) - { - lock (StatusCounts) - { - if (!StatusCounts.ContainsKey(itemStatus)) - return 0; - - return StatusCounts[itemStatus]; - } - } - - /// - /// Increment the hash count for a given hash type - /// - /// Hash type to increment - /// Amount to increment by, defaults to 1 - private void AddHashCount(HashType hashType, long interval = 1) - { - lock (HashCounts) - { - if (!HashCounts.ContainsKey(hashType)) - HashCounts[hashType] = 0; - - HashCounts[hashType] += interval; - if (HashCounts[hashType] < 0) - HashCounts[hashType] = 0; - } - } - - /// - /// Decrement the hash count for a given hash type - /// - /// Hash type to increment - /// Amount to increment by, defaults to 1 - private void RemoveHashCount(HashType hashType, long interval = 1) - { - lock (HashCounts) - { - if (!HashCounts.ContainsKey(hashType)) - return; - - HashCounts[hashType] -= interval; - if (HashCounts[hashType] < 0) - HashCounts[hashType] = 0; - } - } - - /// - /// Increment the item count for a given item type - /// - /// Item type to increment - /// Amount to increment by, defaults to 1 - private void AddItemCount(ItemType itemType, long interval = 1) - { - lock (ItemCounts) - { - if (!ItemCounts.ContainsKey(itemType)) - ItemCounts[itemType] = 0; - - ItemCounts[itemType] += interval; - if (ItemCounts[itemType] < 0) - ItemCounts[itemType] = 0; - } - } - - /// - /// Decrement the item count for a given item type - /// - /// Item type to decrement - /// Amount to increment by, defaults to 1 - private void RemoveItemCount(ItemType itemType, long interval = 1) - { - lock (ItemCounts) - { - if (!ItemCounts.ContainsKey(itemType)) - return; - - ItemCounts[itemType] -= interval; - if (ItemCounts[itemType] < 0) - ItemCounts[itemType] = 0; - } - } - - /// - /// Increment the item count for a given item status - /// - /// Item type to increment - /// Amount to increment by, defaults to 1 - private void AddStatusCount(ItemStatus itemStatus, long interval = 1) - { - lock (StatusCounts) - { - if (!StatusCounts.ContainsKey(itemStatus)) - StatusCounts[itemStatus] = 0; - - StatusCounts[itemStatus] += interval; - if (StatusCounts[itemStatus] < 0) - StatusCounts[itemStatus] = 0; - } - } - - /// - /// Decrement the item count for a given item status - /// - /// Item type to decrement - /// Amount to increment by, defaults to 1 - private void RemoveStatusCount(ItemStatus itemStatus, long interval = 1) - { - lock (StatusCounts) - { - if (!StatusCounts.ContainsKey(itemStatus)) - return; - - StatusCounts[itemStatus] -= interval; - if (StatusCounts[itemStatus] < 0) - StatusCounts[itemStatus] = 0; - } - } - #endregion #region Constructors @@ -932,7 +574,7 @@ namespace SabreTools.DatFiles ConcurrentList output = []; // Check for an empty rom list first - if (TotalCount == 0) + if (DatStatistics.TotalCount == 0) return output; // We want to get the proper key for the DatItem @@ -982,7 +624,7 @@ namespace SabreTools.DatFiles public bool HasDuplicates(DatItem datItem, bool sorted = false) { // Check for an empty rom list first - if (TotalCount == 0) + if (DatStatistics.TotalCount == 0) return false; // We want to get the proper key for the DatItem @@ -1003,7 +645,7 @@ namespace SabreTools.DatFiles public void RecalculateStats() { // Wipe out any stats already there - ResetStatistics(); + DatStatistics.ResetStatistics(); // If we have a blank Dat in any way, return if (items == null) @@ -1018,54 +660,40 @@ namespace SabreTools.DatFiles foreach (DatItem item in datItems) { - AddItemStatistics(item); + DatStatistics.AddItemStatistics(item); } } } - /// - /// Reset all statistics - /// - public void ResetStatistics() - { - TotalCount = 0; - ItemCounts = []; - GameCount = 0; - TotalSize = 0; - HashCounts = []; - StatusCounts = []; - RemovedCount = 0; - } - /// /// Get the highest-order Field value that represents the statistics /// private ItemKey GetBestAvailable() { // Get the required counts - long diskCount = GetItemCount(ItemType.Disk); - long mediaCount = GetItemCount(ItemType.Media); - long romCount = GetItemCount(ItemType.Rom); - long nodumpCount = GetStatusCount(ItemStatus.Nodump); + long diskCount = DatStatistics.GetItemCount(ItemType.Disk); + long mediaCount = DatStatistics.GetItemCount(ItemType.Media); + long romCount = DatStatistics.GetItemCount(ItemType.Rom); + long nodumpCount = DatStatistics.GetStatusCount(ItemStatus.Nodump); // If all items are supposed to have a SHA-512, we bucket by that - if (diskCount + mediaCount + romCount - nodumpCount == GetHashCount(HashType.SHA512)) + if (diskCount + mediaCount + romCount - nodumpCount == DatStatistics.GetHashCount(HashType.SHA512)) return ItemKey.SHA512; // If all items are supposed to have a SHA-384, we bucket by that - else if (diskCount + mediaCount + romCount - nodumpCount == GetHashCount(HashType.SHA384)) + else if (diskCount + mediaCount + romCount - nodumpCount == DatStatistics.GetHashCount(HashType.SHA384)) return ItemKey.SHA384; // If all items are supposed to have a SHA-256, we bucket by that - else if (diskCount + mediaCount + romCount - nodumpCount == GetHashCount(HashType.SHA256)) + else if (diskCount + mediaCount + romCount - nodumpCount == DatStatistics.GetHashCount(HashType.SHA256)) return ItemKey.SHA256; // If all items are supposed to have a SHA-1, we bucket by that - else if (diskCount + mediaCount + romCount - nodumpCount == GetHashCount(HashType.SHA1)) + else if (diskCount + mediaCount + romCount - nodumpCount == DatStatistics.GetHashCount(HashType.SHA1)) return ItemKey.SHA1; // If all items are supposed to have a MD5, we bucket by that - else if (diskCount + mediaCount + romCount - nodumpCount == GetHashCount(HashType.MD5)) + else if (diskCount + mediaCount + romCount - nodumpCount == DatStatistics.GetHashCount(HashType.MD5)) return ItemKey.MD5; // Otherwise, we bucket by CRC diff --git a/SabreTools.DatTools/Rebuilder.cs b/SabreTools.DatTools/Rebuilder.cs index 00c3e420..03e4cb72 100644 --- a/SabreTools.DatTools/Rebuilder.cs +++ b/SabreTools.DatTools/Rebuilder.cs @@ -55,7 +55,7 @@ namespace SabreTools.DatTools #region Perform setup // If the DAT is not populated and inverse is not set, inform the user and quit - if (datFile.Items.TotalCount == 0 && !inverse) + if (datFile.Items.DatStatistics.TotalCount == 0 && !inverse) { logger.User("No entries were found to rebuild, exiting..."); return false; @@ -205,7 +205,7 @@ namespace SabreTools.DatTools #region Perform setup // If the DAT is not populated and inverse is not set, inform the user and quit - if (datFile.Items.TotalCount == 0 && !inverse) + if (datFile.Items.DatStatistics.TotalCount == 0 && !inverse) { logger.User("No entries were found to rebuild, exiting..."); return false; diff --git a/SabreTools.DatTools/Splitter.cs b/SabreTools.DatTools/Splitter.cs index fd1bc214..faac7e88 100644 --- a/SabreTools.DatTools/Splitter.cs +++ b/SabreTools.DatTools/Splitter.cs @@ -42,7 +42,7 @@ namespace SabreTools.DatTools public static (DatFile? extADat, DatFile? extBDat) SplitByExtension(DatFile datFile, List extA, List extB) { // If roms is empty, return false - if (datFile.Items.TotalCount == 0) + if (datFile.Items.DatStatistics.TotalCount == 0) return (null, null); InternalStopwatch watch = new($"Splitting DAT by extension"); diff --git a/SabreTools.DatTools/Statistics.cs b/SabreTools.DatTools/Statistics.cs index 2a1e6d1d..ce23e4d4 100644 --- a/SabreTools.DatTools/Statistics.cs +++ b/SabreTools.DatTools/Statistics.cs @@ -3,6 +3,8 @@ using System.Collections.Generic; using System.IO; using System.Linq; using System.Net; +using System.Runtime.InteropServices.ComTypes; + #if NET40_OR_GREATER || NETCOREAPP using System.Threading.Tasks; #endif @@ -50,7 +52,6 @@ namespace SabreTools.DatTools // Init total DatStatistics totalStats = new() { - Statistics = [], DisplayName = "DIR: All DATs", MachineCount = 0, IsDirectory = true, @@ -60,7 +61,6 @@ namespace SabreTools.DatTools string? lastdir = null; DatStatistics dirStats = new() { - Statistics = [], MachineCount = 0, IsDirectory = true, }; @@ -79,11 +79,10 @@ namespace SabreTools.DatTools #else dirStats.DisplayName = $"DIR: {WebUtility.HtmlEncode(lastdir)}"; #endif - dirStats.MachineCount = dirStats.Statistics.GameCount; + dirStats.MachineCount = dirStats.GameCount; stats.Add(dirStats); dirStats = new DatStatistics { - Statistics = [], MachineCount = 0, IsDirectory = true, }; @@ -97,23 +96,20 @@ namespace SabreTools.DatTools // Add single DAT stats (if asked) if (single) { - DatStatistics individualStats = new() - { - Statistics = datdata.Items, - DisplayName = datdata.Header.GetStringFieldValue(DatHeader.FileNameKey), - MachineCount = datdata.Items.Keys.Count, - IsDirectory = false, - }; + DatStatistics individualStats = datdata.Items.DatStatistics; + individualStats.DisplayName = datdata.Header.GetStringFieldValue(DatHeader.FileNameKey); + individualStats.MachineCount = datdata.Items.Keys.Count; + individualStats.IsDirectory = false; stats.Add(individualStats); } // Add single DAT stats to dir - dirStats.Statistics.AddStatistics(datdata.Items); - dirStats.Statistics.GameCount += datdata.Items.Keys.Count; + dirStats.AddStatistics(datdata.Items.DatStatistics); + dirStats.GameCount += datdata.Items.Keys.Count; // Add single DAT stats to totals - totalStats.Statistics.AddStatistics(datdata.Items); - totalStats.Statistics.GameCount += datdata.Items.Keys.Count; + totalStats.AddStatistics(datdata.Items.DatStatistics); + totalStats.GameCount += datdata.Items.Keys.Count; // Make sure to assign the new directory lastdir = thisdir; @@ -129,12 +125,12 @@ namespace SabreTools.DatTools #else dirStats.DisplayName = $"DIR: {WebUtility.HtmlEncode(lastdir)}"; #endif - dirStats.MachineCount = dirStats.Statistics.GameCount; + dirStats.MachineCount = dirStats.GameCount; stats.Add(dirStats); } // Add total DAT stats - totalStats.MachineCount = totalStats.Statistics.GameCount; + totalStats.MachineCount = totalStats.GameCount; stats.Add(totalStats); return stats; diff --git a/SabreTools.DatTools/Writer.cs b/SabreTools.DatTools/Writer.cs index d8631d14..eefc96f5 100644 --- a/SabreTools.DatTools/Writer.cs +++ b/SabreTools.DatTools/Writer.cs @@ -71,7 +71,7 @@ namespace SabreTools.DatTools datFile.Items.BucketBy(ItemKey.Machine, DedupeType.None); // Output the number of items we're going to be writing - logger.User($"A total of {datFile.Items.TotalCount - datFile.Items.RemovedCount} items will be written out to '{datFile.Header.GetStringFieldValue(DatHeader.FileNameKey)}'"); + logger.User($"A total of {datFile.Items.DatStatistics.TotalCount - datFile.Items.DatStatistics.RemovedCount} items will be written out to '{datFile.Header.GetStringFieldValue(DatHeader.FileNameKey)}'"); // Get the outfile names Dictionary outfiles = datFile.Header.CreateOutFileNames(outDir!, overwrite); @@ -121,24 +121,22 @@ namespace SabreTools.DatTools /// Current DatFile object to write from public static void WriteStatsToConsole(DatFile datFile) { - long diskCount = datFile.Items.GetItemCount(ItemType.Disk); - long mediaCount = datFile.Items.GetItemCount(ItemType.Media); - long romCount = datFile.Items.GetItemCount(ItemType.Rom); + long diskCount = datFile.Items.DatStatistics.GetItemCount(ItemType.Disk); + long mediaCount = datFile.Items.DatStatistics.GetItemCount(ItemType.Media); + long romCount = datFile.Items.DatStatistics.GetItemCount(ItemType.Rom); if (diskCount + mediaCount + romCount == 0) datFile.Items.RecalculateStats(); datFile.Items.BucketBy(ItemKey.Machine, DedupeType.None, norename: true); + datFile.Items.DatStatistics.DisplayName = datFile.Header.GetStringFieldValue(DatHeader.FileNameKey); + datFile.Items.DatStatistics.MachineCount = datFile.Items.Keys.Count; + datFile.Items.DatStatistics.IsDirectory = false; + var statsList = new List { - new() - { - Statistics = datFile.Items, - DisplayName = datFile.Header.GetStringFieldValue(DatHeader.FileNameKey), - MachineCount = datFile.Items.Keys.Count, - IsDirectory = false, - }, + datFile.Items.DatStatistics, }; var consoleOutput = BaseReport.Create(StatReportFormat.None, statsList); consoleOutput!.WriteToFile(null, true, true); @@ -210,11 +208,11 @@ namespace SabreTools.DatTools datFile.Items.RecalculateStats(); // If there's nothing there, abort - if (datFile.Items.TotalCount == 0) + if (datFile.Items.DatStatistics.TotalCount == 0) return false; // If every item is removed, abort - if (datFile.Items.TotalCount == datFile.Items.RemovedCount) + if (datFile.Items.DatStatistics.TotalCount == datFile.Items.DatStatistics.RemovedCount) return false; return true; diff --git a/SabreTools.Reports/BaseReport.cs b/SabreTools.Reports/BaseReport.cs index de004425..a56f0555 100644 --- a/SabreTools.Reports/BaseReport.cs +++ b/SabreTools.Reports/BaseReport.cs @@ -1,5 +1,5 @@ using System.Collections.Generic; - +using SabreTools.DatFiles; using SabreTools.Logging; using SabreTools.Reports.Formats; diff --git a/SabreTools.Reports/DatStatistics.cs b/SabreTools.Reports/DatStatistics.cs deleted file mode 100644 index ce9bce30..00000000 --- a/SabreTools.Reports/DatStatistics.cs +++ /dev/null @@ -1,30 +0,0 @@ -using SabreTools.DatFiles; - -namespace SabreTools.Reports -{ - /// - /// Statistics wrapper for outputting - /// - public class DatStatistics - { - /// - /// ItemDictionary representing the statistics - /// - public ItemDictionary? Statistics { get; set; } - - /// - /// Name to display on output - /// - public string? DisplayName { get; set; } - - /// - /// Total machine count to use on output - /// - public long MachineCount { get; set; } - - /// - /// Determines if statistics are for a directory or not - /// - public bool IsDirectory { get; set; } = false; - } -} diff --git a/SabreTools.Reports/Formats/Html.cs b/SabreTools.Reports/Formats/Html.cs index caa1d9be..30763d79 100644 --- a/SabreTools.Reports/Formats/Html.cs +++ b/SabreTools.Reports/Formats/Html.cs @@ -4,6 +4,7 @@ using System.IO; using System.Net; using System.Text; using System.Xml; +using SabreTools.DatFiles; using SabreTools.DatItems; using SabreTools.Hashing; using SabreTools.Logging; @@ -228,7 +229,7 @@ body { xtw.WriteStartElement("td"); xtw.WriteAttributeString("align", "right"); - xtw.WriteString(GetBytesReadable(stat.Statistics!.TotalSize)); + xtw.WriteString(GetBytesReadable(stat.TotalSize)); xtw.WriteEndElement(); // td xtw.WriteStartElement("td"); @@ -238,39 +239,39 @@ body { xtw.WriteStartElement("td"); xtw.WriteAttributeString("align", "right"); - xtw.WriteString(stat.Statistics.GetItemCount(ItemType.Rom).ToString()); + xtw.WriteString(stat.GetItemCount(ItemType.Rom).ToString()); xtw.WriteEndElement(); // td xtw.WriteStartElement("td"); xtw.WriteAttributeString("align", "right"); - xtw.WriteString(stat.Statistics.GetItemCount(ItemType.Disk).ToString()); + xtw.WriteString(stat.GetItemCount(ItemType.Disk).ToString()); xtw.WriteEndElement(); // td xtw.WriteStartElement("td"); xtw.WriteAttributeString("align", "right"); - xtw.WriteString(stat.Statistics.GetHashCount(HashType.CRC32).ToString()); + xtw.WriteString(stat.GetHashCount(HashType.CRC32).ToString()); xtw.WriteEndElement(); // td xtw.WriteStartElement("td"); xtw.WriteAttributeString("align", "right"); - xtw.WriteString(stat.Statistics.GetHashCount(HashType.MD5).ToString()); + xtw.WriteString(stat.GetHashCount(HashType.MD5).ToString()); xtw.WriteEndElement(); // td xtw.WriteStartElement("td"); xtw.WriteAttributeString("align", "right"); - xtw.WriteString(stat.Statistics.GetHashCount(HashType.SHA1).ToString()); + xtw.WriteString(stat.GetHashCount(HashType.SHA1).ToString()); xtw.WriteEndElement(); // td xtw.WriteStartElement("td"); xtw.WriteAttributeString("align", "right"); - xtw.WriteString(stat.Statistics.GetHashCount(HashType.SHA256).ToString()); + xtw.WriteString(stat.GetHashCount(HashType.SHA256).ToString()); xtw.WriteEndElement(); // td if (baddumpCol) { xtw.WriteStartElement("td"); xtw.WriteAttributeString("align", "right"); - xtw.WriteString(stat.Statistics.GetStatusCount(ItemStatus.BadDump).ToString()); + xtw.WriteString(stat.GetStatusCount(ItemStatus.BadDump).ToString()); xtw.WriteEndElement(); // td } @@ -278,7 +279,7 @@ body { { xtw.WriteStartElement("td"); xtw.WriteAttributeString("align", "right"); - xtw.WriteString(stat.Statistics.GetStatusCount(ItemStatus.Nodump).ToString()); + xtw.WriteString(stat.GetStatusCount(ItemStatus.Nodump).ToString()); xtw.WriteEndElement(); // td } diff --git a/SabreTools.Reports/Formats/SeparatedValue.cs b/SabreTools.Reports/Formats/SeparatedValue.cs index 99dea849..01237895 100644 --- a/SabreTools.Reports/Formats/SeparatedValue.cs +++ b/SabreTools.Reports/Formats/SeparatedValue.cs @@ -2,6 +2,7 @@ using System.Collections.Generic; using System.IO; using System.Text; +using SabreTools.DatFiles; using SabreTools.DatItems; using SabreTools.Hashing; using SabreTools.IO.Writers; @@ -130,18 +131,18 @@ namespace SabreTools.Reports.Formats string[] values = [ stat.DisplayName!, - stat.Statistics!.TotalSize.ToString(), + stat.TotalSize.ToString(), stat.MachineCount.ToString(), - stat.Statistics.GetItemCount(ItemType.Rom).ToString(), - stat.Statistics.GetItemCount(ItemType.Disk).ToString(), - stat.Statistics.GetHashCount(HashType.CRC32).ToString(), - stat.Statistics.GetHashCount(HashType.MD5).ToString(), - stat.Statistics.GetHashCount(HashType.SHA1).ToString(), - stat.Statistics.GetHashCount(HashType.SHA256).ToString(), - stat.Statistics.GetHashCount(HashType.SHA384).ToString(), - stat.Statistics.GetHashCount(HashType.SHA512).ToString(), - baddumpCol ? stat.Statistics.GetStatusCount(ItemStatus.BadDump).ToString() : string.Empty, - nodumpCol ? stat.Statistics.GetStatusCount(ItemStatus.Nodump).ToString() : string.Empty, + stat.GetItemCount(ItemType.Rom).ToString(), + stat.GetItemCount(ItemType.Disk).ToString(), + stat.GetHashCount(HashType.CRC32).ToString(), + stat.GetHashCount(HashType.MD5).ToString(), + stat.GetHashCount(HashType.SHA1).ToString(), + stat.GetHashCount(HashType.SHA256).ToString(), + stat.GetHashCount(HashType.SHA384).ToString(), + stat.GetHashCount(HashType.SHA512).ToString(), + baddumpCol ? stat.GetStatusCount(ItemStatus.BadDump).ToString() : string.Empty, + nodumpCol ? stat.GetStatusCount(ItemStatus.Nodump).ToString() : string.Empty, ]; svw.WriteValues(values); svw.Flush(); diff --git a/SabreTools.Reports/Formats/Textfile.cs b/SabreTools.Reports/Formats/Textfile.cs index f2e71fee..ffb53c9a 100644 --- a/SabreTools.Reports/Formats/Textfile.cs +++ b/SabreTools.Reports/Formats/Textfile.cs @@ -1,6 +1,7 @@ using System; using System.Collections.Generic; using System.IO; +using SabreTools.DatFiles; using SabreTools.DatItems; using SabreTools.Hashing; using SabreTools.Logging; @@ -92,22 +93,22 @@ namespace SabreTools.Reports.Formats { string line = @"'" + stat.DisplayName + @"': -------------------------------------------------- - Uncompressed size: " + GetBytesReadable(stat.Statistics!.TotalSize) + @" + Uncompressed size: " + GetBytesReadable(stat!.TotalSize) + @" Games found: " + stat.MachineCount + @" - Roms found: " + stat.Statistics.GetItemCount(ItemType.Rom) + @" - Disks found: " + stat.Statistics.GetItemCount(ItemType.Disk) + @" - Roms with CRC: " + stat.Statistics.GetHashCount(HashType.CRC32) + @" - Roms with MD5: " + stat.Statistics.GetHashCount(HashType.MD5) + @" - Roms with SHA-1: " + stat.Statistics.GetHashCount(HashType.SHA1) + @" - Roms with SHA-256: " + stat.Statistics.GetHashCount(HashType.SHA256) + @" - Roms with SHA-384: " + stat.Statistics.GetHashCount(HashType.SHA384) + @" - Roms with SHA-512: " + stat.Statistics.GetHashCount(HashType.SHA512) + "\n"; + Roms found: " + stat.GetItemCount(ItemType.Rom) + @" + Disks found: " + stat.GetItemCount(ItemType.Disk) + @" + Roms with CRC: " + stat.GetHashCount(HashType.CRC32) + @" + Roms with MD5: " + stat.GetHashCount(HashType.MD5) + @" + Roms with SHA-1: " + stat.GetHashCount(HashType.SHA1) + @" + Roms with SHA-256: " + stat.GetHashCount(HashType.SHA256) + @" + Roms with SHA-384: " + stat.GetHashCount(HashType.SHA384) + @" + Roms with SHA-512: " + stat.GetHashCount(HashType.SHA512) + "\n"; if (baddumpCol) - line += " Roms with BadDump status: " + stat.Statistics.GetStatusCount(ItemStatus.BadDump) + "\n"; + line += " Roms with BadDump status: " + stat.GetStatusCount(ItemStatus.BadDump) + "\n"; if (nodumpCol) - line += " Roms with Nodump status: " + stat.Statistics.GetStatusCount(ItemStatus.Nodump) + "\n"; + line += " Roms with Nodump status: " + stat.GetStatusCount(ItemStatus.Nodump) + "\n"; // For spacing between DATs line += "\n\n"; diff --git a/SabreTools.Test/DatFiles/ItemDictionaryTests.cs b/SabreTools.Test/DatFiles/ItemDictionaryTests.cs index dda569ee..a61f4788 100644 --- a/SabreTools.Test/DatFiles/ItemDictionaryTests.cs +++ b/SabreTools.Test/DatFiles/ItemDictionaryTests.cs @@ -189,9 +189,10 @@ namespace SabreTools.Test.DatFiles [Fact] public void ResetStatisticsTest() { - var dict = new ItemDictionary { GameCount = 1 }; - dict.ResetStatistics(); - Assert.Equal(0, dict.GameCount); + var dict = new ItemDictionary(); + dict.DatStatistics.GameCount = 1; + dict.DatStatistics.ResetStatistics(); + Assert.Equal(0, dict.DatStatistics.GameCount); } } } \ No newline at end of file diff --git a/SabreTools.Test/DatTools/ParserTests.cs b/SabreTools.Test/DatTools/ParserTests.cs index d441d5d7..d0abfb13 100644 --- a/SabreTools.Test/DatTools/ParserTests.cs +++ b/SabreTools.Test/DatTools/ParserTests.cs @@ -43,7 +43,7 @@ namespace SabreTools.Test.DatTools var datFile = SabreTools.DatTools.Parser.CreateAndParse(filename, throwOnError: true); Assert.Equal(datFormat, datFile.Header.GetFieldValue(DatHeader.DatFormatKey)); - Assert.Equal(totalCount, datFile.Items.TotalCount); + Assert.Equal(totalCount, datFile.Items.DatStatistics.TotalCount); } } } \ No newline at end of file