Skip to content

Adopt MoreLINQ; remove duplicated collection extensions #355

Open

Description

@ChrisonSimtian

Tier 2 — Consolidate. src/Fallout.Utilities/Collections/ (~900 LOC, 23 files) contains many LINQ-like helpers that duplicate MoreLINQ: Enumerable.Distinct.cs (DistinctBy), Enumerable.Random.cs (Random/Shuffle), Enumerable.TakeUntil.cs, Enumerable.ForEach.cs.

Action

Add MoreLINQ; delete the duplicated helpers and redirect call sites.

Keep (genuinely Fallout-specific — do NOT delete)

  • Enumerable.TopologicalSort.cs (cycle-detecting sort used for target ordering)
  • LookupTable.cs (mutable ILookup — no BCL/MoreLINQ equivalent)
  • Enumerable.SingleOrDefaultOrError.cs / Enumerable.ToDictionary.cs (custom diagnostic messages)

⚠️ Breaking change

These are public extension methods. Removal breaks consumers → breaking-change, experimental, batched to yearly major, CHANGELOG migration note. Where feasible, keep [Obsolete] forwarders.

Acceptance

  • MoreLINQ added to Directory.Packages.props
  • Duplicated Distinct/Random/TakeUntil/ForEach helpers removed or obsoleted
  • Fallout-specific helpers retained
  • CHANGELOG entry + migration note

From dependency-consolidation audit, 2026-06-02.

Activity

  1. added
    enhancementNew feature or request
    breaking-changeChange is breaking — requires major version bump per CLAUDE.md semver policy.
    on Jun 2, 2026
  2. ChrisonSimtian commented on Jun 3, 2026

    @ChrisonSimtian
    CollaboratorAuthor

    Insights from a discarded prototype (old paths; map to onion structure after #359).

    • Package: MoreLinq 4.4.0 (central).
    • Only 2 genuine duplicates: DistinctBy and Shuffle (was Randomize). Replace via [Obsolete] forwarders.
    • KEEP these — not real duplicates:
      • TakeUntil/SkipUntil: ours is EXCLUSIVE, MoreLINQ's is INCLUSIVE. Swapping silently changes ArgumentParser + CompletionUtility.
      • ForEach/ForEachLazy: MoreLINQ has no Action<T,int> index overload and no ForEachLazy; ~70 callers.
      • single-pick Random<T>(): no MoreLINQ/BCL equivalent.
    • Gotcha: net10 BCL now ships DistinctBy/Shuffle, which collide with MoreLINQ's extensions. Call MoreLinq.MoreEnumerable.* explicitly so both netstandard2.0 and net10.0 resolve.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    breaking-changeChange is breaking — requires major version bump per CLAUDE.md semver policy.enhancementNew feature or requesttarget/vCurrentTargets the current version

    Type

    No type

    Projects

    No projects

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions