diff --git a/.github/workflows/dotnet.yml b/.github/workflows/dotnet.yml
index a190a6f..07f51cd 100644
--- a/.github/workflows/dotnet.yml
+++ b/.github/workflows/dotnet.yml
@@ -1,28 +1,28 @@
-# This workflow will build a .NET project
-# For more information see: https://docs.github.com/en/actions/automating-builds-and-tests/building-and-testing-net
-
-name: .NET
-
-on:
- push:
- branches: [ "main" ]
- pull_request:
- branches: [ "main" ]
-
-jobs:
- build:
-
- runs-on: ubuntu-latest
-
- steps:
- - uses: actions/checkout@v3
- - name: Setup .NET
- uses: actions/setup-dotnet@v3
- with:
- dotnet-version: 8.0.x
- - name: Restore dependencies
- run: dotnet restore
- - name: Build
- run: dotnet build --no-restore
- - name: Test
- run: dotnet test --framework net8.0 --verbosity normal
+# This workflow will build a .NET project
+# For more information see: https://docs.github.com/en/actions/automating-builds-and-tests/building-and-testing-net
+
+name: .NET
+
+on:
+ push:
+ branches: [ "main" ]
+ pull_request:
+ branches: [ "main" ]
+
+jobs:
+ build:
+
+ runs-on: ubuntu-latest
+
+ steps:
+ - uses: actions/checkout@v3
+ - name: Setup .NET
+ uses: actions/setup-dotnet@v3
+ with:
+ dotnet-version: 8.0.x
+ - name: Restore dependencies
+ run: dotnet restore
+ - name: Build
+ run: dotnet build --no-restore
+ - name: Test
+ run: dotnet test --framework net8.0 --verbosity normal
diff --git a/.gitignore b/.gitignore
index dfcfd56..cb43218 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,350 +1,350 @@
-## Ignore Visual Studio temporary files, build results, and
-## files generated by popular Visual Studio add-ons.
-##
-## Get latest from https://github.com/github/gitignore/blob/master/VisualStudio.gitignore
-
-# User-specific files
-*.rsuser
-*.suo
-*.user
-*.userosscache
-*.sln.docstates
-
-# User-specific files (MonoDevelop/Xamarin Studio)
-*.userprefs
-
-# Mono auto generated files
-mono_crash.*
-
-# Build results
-[Dd]ebug/
-[Dd]ebugPublic/
-[Rr]elease/
-[Rr]eleases/
-x64/
-x86/
-[Aa][Rr][Mm]/
-[Aa][Rr][Mm]64/
-bld/
-[Bb]in/
-[Oo]bj/
-[Ll]og/
-[Ll]ogs/
-
-# Visual Studio 2015/2017 cache/options directory
-.vs/
-# Uncomment if you have tasks that create the project's static files in wwwroot
-#wwwroot/
-
-# Visual Studio 2017 auto generated files
-Generated\ Files/
-
-# MSTest test Results
-[Tt]est[Rr]esult*/
-[Bb]uild[Ll]og.*
-
-# NUnit
-*.VisualState.xml
-TestResult.xml
-nunit-*.xml
-
-# Build Results of an ATL Project
-[Dd]ebugPS/
-[Rr]eleasePS/
-dlldata.c
-
-# Benchmark Results
-BenchmarkDotNet.Artifacts/
-
-# .NET Core
-project.lock.json
-project.fragment.lock.json
-artifacts/
-
-# StyleCop
-StyleCopReport.xml
-
-# Files built by Visual Studio
-*_i.c
-*_p.c
-*_h.h
-*.ilk
-*.meta
-*.obj
-*.iobj
-*.pch
-*.pdb
-*.ipdb
-*.pgc
-*.pgd
-*.rsp
-*.sbr
-*.tlb
-*.tli
-*.tlh
-*.tmp
-*.tmp_proj
-*_wpftmp.csproj
-*.log
-*.vspscc
-*.vssscc
-.builds
-*.pidb
-*.svclog
-*.scc
-
-# Chutzpah Test files
-_Chutzpah*
-
-# Visual C++ cache files
-ipch/
-*.aps
-*.ncb
-*.opendb
-*.opensdf
-*.sdf
-*.cachefile
-*.VC.db
-*.VC.VC.opendb
-
-# Visual Studio profiler
-*.psess
-*.vsp
-*.vspx
-*.sap
-
-# Visual Studio Trace Files
-*.e2e
-
-# TFS 2012 Local Workspace
-$tf/
-
-# Guidance Automation Toolkit
-*.gpState
-
-# ReSharper is a .NET coding add-in
-_ReSharper*/
-*.[Rr]e[Ss]harper
-*.DotSettings.user
-
-# TeamCity is a build add-in
-_TeamCity*
-
-# DotCover is a Code Coverage Tool
-*.dotCover
-
-# AxoCover is a Code Coverage Tool
-.axoCover/*
-!.axoCover/settings.json
-
-# Visual Studio code coverage results
-*.coverage
-*.coveragexml
-
-# NCrunch
-_NCrunch_*
-.*crunch*.local.xml
-nCrunchTemp_*
-
-# MightyMoose
-*.mm.*
-AutoTest.Net/
-
-# Web workbench (sass)
-.sass-cache/
-
-# Installshield output folder
-[Ee]xpress/
-
-# DocProject is a documentation generator add-in
-DocProject/buildhelp/
-DocProject/Help/*.HxT
-DocProject/Help/*.HxC
-DocProject/Help/*.hhc
-DocProject/Help/*.hhk
-DocProject/Help/*.hhp
-DocProject/Help/Html2
-DocProject/Help/html
-
-# Click-Once directory
-publish/
-
-# Publish Web Output
-*.[Pp]ublish.xml
-*.azurePubxml
-# Note: Comment the next line if you want to checkin your web deploy settings,
-# but database connection strings (with potential passwords) will be unencrypted
-*.pubxml
-*.publishproj
-
-# Microsoft Azure Web App publish settings. Comment the next line if you want to
-# checkin your Azure Web App publish settings, but sensitive information contained
-# in these scripts will be unencrypted
-PublishScripts/
-
-# NuGet Packages
-*.nupkg
-# NuGet Symbol Packages
-*.snupkg
-# The packages folder can be ignored because of Package Restore
-**/[Pp]ackages/*
-# except build/, which is used as an MSBuild target.
-!**/[Pp]ackages/build/
-# Uncomment if necessary however generally it will be regenerated when needed
-#!**/[Pp]ackages/repositories.config
-# NuGet v3's project.json files produces more ignorable files
-*.nuget.props
-*.nuget.targets
-
-# Microsoft Azure Build Output
-csx/
-*.build.csdef
-
-# Microsoft Azure Emulator
-ecf/
-rcf/
-
-# Windows Store app package directories and files
-AppPackages/
-BundleArtifacts/
-Package.StoreAssociation.xml
-_pkginfo.txt
-*.appx
-*.appxbundle
-*.appxupload
-
-# Visual Studio cache files
-# files ending in .cache can be ignored
-*.[Cc]ache
-# but keep track of directories ending in .cache
-!?*.[Cc]ache/
-
-# Others
-ClientBin/
-~$*
-*~
-*.dbmdl
-*.dbproj.schemaview
-*.jfm
-*.pfx
-*.publishsettings
-orleans.codegen.cs
-
-# Including strong name files can present a security risk
-# (https://github.com/github/gitignore/pull/2483#issue-259490424)
-#*.snk
-
-# Since there are multiple workflows, uncomment next line to ignore bower_components
-# (https://github.com/github/gitignore/pull/1529#issuecomment-104372622)
-#bower_components/
-
-# RIA/Silverlight projects
-Generated_Code/
-
-# Backup & report files from converting an old project file
-# to a newer Visual Studio version. Backup files are not needed,
-# because we have git ;-)
-_UpgradeReport_Files/
-Backup*/
-UpgradeLog*.XML
-UpgradeLog*.htm
-ServiceFabricBackup/
-*.rptproj.bak
-
-# SQL Server files
-*.mdf
-*.ldf
-*.ndf
-
-# Business Intelligence projects
-*.rdl.data
-*.bim.layout
-*.bim_*.settings
-*.rptproj.rsuser
-*- [Bb]ackup.rdl
-*- [Bb]ackup ([0-9]).rdl
-*- [Bb]ackup ([0-9][0-9]).rdl
-
-# Microsoft Fakes
-FakesAssemblies/
-
-# GhostDoc plugin setting file
-*.GhostDoc.xml
-
-# Node.js Tools for Visual Studio
-.ntvs_analysis.dat
-node_modules/
-
-# Visual Studio 6 build log
-*.plg
-
-# Visual Studio 6 workspace options file
-*.opt
-
-# Visual Studio 6 auto-generated workspace file (contains which files were open etc.)
-*.vbw
-
-# Visual Studio LightSwitch build output
-**/*.HTMLClient/GeneratedArtifacts
-**/*.DesktopClient/GeneratedArtifacts
-**/*.DesktopClient/ModelManifest.xml
-**/*.Server/GeneratedArtifacts
-**/*.Server/ModelManifest.xml
-_Pvt_Extensions
-
-# Paket dependency manager
-.paket/paket.exe
-paket-files/
-
-# FAKE - F# Make
-.fake/
-
-# CodeRush personal settings
-.cr/personal
-
-# Python Tools for Visual Studio (PTVS)
-__pycache__/
-*.pyc
-
-# Cake - Uncomment if you are using it
-# tools/**
-# !tools/packages.config
-
-# Tabs Studio
-*.tss
-
-# Telerik's JustMock configuration file
-*.jmconfig
-
-# BizTalk build output
-*.btp.cs
-*.btm.cs
-*.odx.cs
-*.xsd.cs
-
-# OpenCover UI analysis results
-OpenCover/
-
-# Azure Stream Analytics local run output
-ASALocalRun/
-
-# MSBuild Binary and Structured Log
-*.binlog
-
-# NVidia Nsight GPU debugger configuration file
-*.nvuser
-
-# MFractors (Xamarin productivity tool) working folder
-.mfractor/
-
-# Local History for Visual Studio
-.localhistory/
-
-# BeatPulse healthcheck temp database
-healthchecksdb
-
-# Backup folder for Package Reference Convert tool in Visual Studio 2017
-MigrationBackup/
-
-# Ionide (cross platform F# VS Code tools) working folder
-.ionide/
+## Ignore Visual Studio temporary files, build results, and
+## files generated by popular Visual Studio add-ons.
+##
+## Get latest from https://github.com/github/gitignore/blob/master/VisualStudio.gitignore
+
+# User-specific files
+*.rsuser
+*.suo
+*.user
+*.userosscache
+*.sln.docstates
+
+# User-specific files (MonoDevelop/Xamarin Studio)
+*.userprefs
+
+# Mono auto generated files
+mono_crash.*
+
+# Build results
+[Dd]ebug/
+[Dd]ebugPublic/
+[Rr]elease/
+[Rr]eleases/
+x64/
+x86/
+[Aa][Rr][Mm]/
+[Aa][Rr][Mm]64/
+bld/
+[Bb]in/
+[Oo]bj/
+[Ll]og/
+[Ll]ogs/
+
+# Visual Studio 2015/2017 cache/options directory
+.vs/
+# Uncomment if you have tasks that create the project's static files in wwwroot
+#wwwroot/
+
+# Visual Studio 2017 auto generated files
+Generated\ Files/
+
+# MSTest test Results
+[Tt]est[Rr]esult*/
+[Bb]uild[Ll]og.*
+
+# NUnit
+*.VisualState.xml
+TestResult.xml
+nunit-*.xml
+
+# Build Results of an ATL Project
+[Dd]ebugPS/
+[Rr]eleasePS/
+dlldata.c
+
+# Benchmark Results
+BenchmarkDotNet.Artifacts/
+
+# .NET Core
+project.lock.json
+project.fragment.lock.json
+artifacts/
+
+# StyleCop
+StyleCopReport.xml
+
+# Files built by Visual Studio
+*_i.c
+*_p.c
+*_h.h
+*.ilk
+*.meta
+*.obj
+*.iobj
+*.pch
+*.pdb
+*.ipdb
+*.pgc
+*.pgd
+*.rsp
+*.sbr
+*.tlb
+*.tli
+*.tlh
+*.tmp
+*.tmp_proj
+*_wpftmp.csproj
+*.log
+*.vspscc
+*.vssscc
+.builds
+*.pidb
+*.svclog
+*.scc
+
+# Chutzpah Test files
+_Chutzpah*
+
+# Visual C++ cache files
+ipch/
+*.aps
+*.ncb
+*.opendb
+*.opensdf
+*.sdf
+*.cachefile
+*.VC.db
+*.VC.VC.opendb
+
+# Visual Studio profiler
+*.psess
+*.vsp
+*.vspx
+*.sap
+
+# Visual Studio Trace Files
+*.e2e
+
+# TFS 2012 Local Workspace
+$tf/
+
+# Guidance Automation Toolkit
+*.gpState
+
+# ReSharper is a .NET coding add-in
+_ReSharper*/
+*.[Rr]e[Ss]harper
+*.DotSettings.user
+
+# TeamCity is a build add-in
+_TeamCity*
+
+# DotCover is a Code Coverage Tool
+*.dotCover
+
+# AxoCover is a Code Coverage Tool
+.axoCover/*
+!.axoCover/settings.json
+
+# Visual Studio code coverage results
+*.coverage
+*.coveragexml
+
+# NCrunch
+_NCrunch_*
+.*crunch*.local.xml
+nCrunchTemp_*
+
+# MightyMoose
+*.mm.*
+AutoTest.Net/
+
+# Web workbench (sass)
+.sass-cache/
+
+# Installshield output folder
+[Ee]xpress/
+
+# DocProject is a documentation generator add-in
+DocProject/buildhelp/
+DocProject/Help/*.HxT
+DocProject/Help/*.HxC
+DocProject/Help/*.hhc
+DocProject/Help/*.hhk
+DocProject/Help/*.hhp
+DocProject/Help/Html2
+DocProject/Help/html
+
+# Click-Once directory
+publish/
+
+# Publish Web Output
+*.[Pp]ublish.xml
+*.azurePubxml
+# Note: Comment the next line if you want to checkin your web deploy settings,
+# but database connection strings (with potential passwords) will be unencrypted
+*.pubxml
+*.publishproj
+
+# Microsoft Azure Web App publish settings. Comment the next line if you want to
+# checkin your Azure Web App publish settings, but sensitive information contained
+# in these scripts will be unencrypted
+PublishScripts/
+
+# NuGet Packages
+*.nupkg
+# NuGet Symbol Packages
+*.snupkg
+# The packages folder can be ignored because of Package Restore
+**/[Pp]ackages/*
+# except build/, which is used as an MSBuild target.
+!**/[Pp]ackages/build/
+# Uncomment if necessary however generally it will be regenerated when needed
+#!**/[Pp]ackages/repositories.config
+# NuGet v3's project.json files produces more ignorable files
+*.nuget.props
+*.nuget.targets
+
+# Microsoft Azure Build Output
+csx/
+*.build.csdef
+
+# Microsoft Azure Emulator
+ecf/
+rcf/
+
+# Windows Store app package directories and files
+AppPackages/
+BundleArtifacts/
+Package.StoreAssociation.xml
+_pkginfo.txt
+*.appx
+*.appxbundle
+*.appxupload
+
+# Visual Studio cache files
+# files ending in .cache can be ignored
+*.[Cc]ache
+# but keep track of directories ending in .cache
+!?*.[Cc]ache/
+
+# Others
+ClientBin/
+~$*
+*~
+*.dbmdl
+*.dbproj.schemaview
+*.jfm
+*.pfx
+*.publishsettings
+orleans.codegen.cs
+
+# Including strong name files can present a security risk
+# (https://github.com/github/gitignore/pull/2483#issue-259490424)
+#*.snk
+
+# Since there are multiple workflows, uncomment next line to ignore bower_components
+# (https://github.com/github/gitignore/pull/1529#issuecomment-104372622)
+#bower_components/
+
+# RIA/Silverlight projects
+Generated_Code/
+
+# Backup & report files from converting an old project file
+# to a newer Visual Studio version. Backup files are not needed,
+# because we have git ;-)
+_UpgradeReport_Files/
+Backup*/
+UpgradeLog*.XML
+UpgradeLog*.htm
+ServiceFabricBackup/
+*.rptproj.bak
+
+# SQL Server files
+*.mdf
+*.ldf
+*.ndf
+
+# Business Intelligence projects
+*.rdl.data
+*.bim.layout
+*.bim_*.settings
+*.rptproj.rsuser
+*- [Bb]ackup.rdl
+*- [Bb]ackup ([0-9]).rdl
+*- [Bb]ackup ([0-9][0-9]).rdl
+
+# Microsoft Fakes
+FakesAssemblies/
+
+# GhostDoc plugin setting file
+*.GhostDoc.xml
+
+# Node.js Tools for Visual Studio
+.ntvs_analysis.dat
+node_modules/
+
+# Visual Studio 6 build log
+*.plg
+
+# Visual Studio 6 workspace options file
+*.opt
+
+# Visual Studio 6 auto-generated workspace file (contains which files were open etc.)
+*.vbw
+
+# Visual Studio LightSwitch build output
+**/*.HTMLClient/GeneratedArtifacts
+**/*.DesktopClient/GeneratedArtifacts
+**/*.DesktopClient/ModelManifest.xml
+**/*.Server/GeneratedArtifacts
+**/*.Server/ModelManifest.xml
+_Pvt_Extensions
+
+# Paket dependency manager
+.paket/paket.exe
+paket-files/
+
+# FAKE - F# Make
+.fake/
+
+# CodeRush personal settings
+.cr/personal
+
+# Python Tools for Visual Studio (PTVS)
+__pycache__/
+*.pyc
+
+# Cake - Uncomment if you are using it
+# tools/**
+# !tools/packages.config
+
+# Tabs Studio
+*.tss
+
+# Telerik's JustMock configuration file
+*.jmconfig
+
+# BizTalk build output
+*.btp.cs
+*.btm.cs
+*.odx.cs
+*.xsd.cs
+
+# OpenCover UI analysis results
+OpenCover/
+
+# Azure Stream Analytics local run output
+ASALocalRun/
+
+# MSBuild Binary and Structured Log
+*.binlog
+
+# NVidia Nsight GPU debugger configuration file
+*.nvuser
+
+# MFractors (Xamarin productivity tool) working folder
+.mfractor/
+
+# Local History for Visual Studio
+.localhistory/
+
+# BeatPulse healthcheck temp database
+healthchecksdb
+
+# Backup folder for Package Reference Convert tool in Visual Studio 2017
+MigrationBackup/
+
+# Ionide (cross platform F# VS Code tools) working folder
+.ionide/
diff --git a/.vscode/launch.json b/.vscode/launch.json
index 34abc08..a65dc43 100644
--- a/.vscode/launch.json
+++ b/.vscode/launch.json
@@ -1,26 +1,26 @@
-{
- "version": "0.2.0",
- "configurations": [
- {
- // Use IntelliSense to find out which attributes exist for C# debugging
- // Use hover for the description of the existing attributes
- // For further information visit https://github.com/OmniSharp/omnisharp-vscode/blob/master/debugger-launchjson.md
- "name": ".NET Core Launch (console)",
- "type": "coreclr",
- "request": "launch",
- "preLaunchTask": "build",
- // If you have changed target frameworks, make sure to update the program path.
- "program": "${workspaceFolder}/Recyclable.Collections.Benchmarks/bin/Debug/net8.0/Recyclable.Collections.Benchmarks.dll",
- "args": [],
- "cwd": "${workspaceFolder}/Recyclable.Collections.Benchmarks",
- // For more information about the 'console' field, see https://aka.ms/VSCode-CS-LaunchJson-Console
- "console": "internalConsole",
- "stopAtEntry": false
- },
- {
- "name": ".NET Core Attach",
- "type": "coreclr",
- "request": "attach"
- }
- ]
+{
+ "version": "0.2.0",
+ "configurations": [
+ {
+ // Use IntelliSense to find out which attributes exist for C# debugging
+ // Use hover for the description of the existing attributes
+ // For further information visit https://github.com/OmniSharp/omnisharp-vscode/blob/master/debugger-launchjson.md
+ "name": ".NET Core Launch (console)",
+ "type": "coreclr",
+ "request": "launch",
+ "preLaunchTask": "build",
+ // If you have changed target frameworks, make sure to update the program path.
+ "program": "${workspaceFolder}/Recyclable.Collections.Benchmarks/bin/Debug/net8.0/Recyclable.Collections.Benchmarks.dll",
+ "args": [],
+ "cwd": "${workspaceFolder}/Recyclable.Collections.Benchmarks",
+ // For more information about the 'console' field, see https://aka.ms/VSCode-CS-LaunchJson-Console
+ "console": "internalConsole",
+ "stopAtEntry": false
+ },
+ {
+ "name": ".NET Core Attach",
+ "type": "coreclr",
+ "request": "attach"
+ }
+ ]
}
\ No newline at end of file
diff --git a/.vscode/settings.json b/.vscode/settings.json
new file mode 100644
index 0000000..9e26dfe
--- /dev/null
+++ b/.vscode/settings.json
@@ -0,0 +1 @@
+{}
\ No newline at end of file
diff --git a/.vscode/tasks.json b/.vscode/tasks.json
index d67f306..3b18015 100644
--- a/.vscode/tasks.json
+++ b/.vscode/tasks.json
@@ -1,73 +1,73 @@
-{
- "version": "2.0.0",
- "tasks": [
- {
- "isBuildCommand": true,
- "label": "build",
- "dependsOn": ["build debug", "build release"],
- "problemMatcher": "$msCompile",
- "group": {
- "kind": "build",
- "isDefault": true
- }
- },
- {
- "isBuildCommand": true,
- "label": "build debug",
- "command": "dotnet",
- "type": "process",
- "args": [
- "build",
- "${workspaceFolder}/Recyclable.Collections.sln",
- "/property:GenerateFullPaths=true",
- "/consoleloggerparameters:NoSummary",
- ],
- "problemMatcher": "$msCompile",
- "group": {
- "kind": "build",
- "isDefault": false
- }
- },
- {
- "label": "build release",
- "command": "dotnet",
- "type": "process",
- "args": [
- "build",
- "${workspaceFolder}/Recyclable.Collections.sln",
- "/property:GenerateFullPaths=true",
- "/consoleloggerparameters:NoSummary",
- "-c", "Release",
- ],
- "problemMatcher": "$msCompile",
- "group": {
- "kind": "build",
- "isDefault": false
- }
- },
- {
- "label": "publish",
- "command": "dotnet",
- "type": "process",
- "args": [
- "publish",
- "${workspaceFolder}/Recyclable.Collections.sln",
- "/property:GenerateFullPaths=true",
- "/consoleloggerparameters:NoSummary"
- ],
- "problemMatcher": "$msCompile"
- },
- {
- "label": "watch",
- "command": "dotnet",
- "type": "process",
- "args": [
- "watch",
- "run",
- "--project",
- "${workspaceFolder}/Recyclable.Collections.sln"
- ],
- "problemMatcher": "$msCompile"
- }
- ]
+{
+ "version": "2.0.0",
+ "tasks": [
+ {
+ "isBuildCommand": true,
+ "label": "build",
+ "dependsOn": ["build debug", "build release"],
+ "problemMatcher": "$msCompile",
+ "group": {
+ "kind": "build",
+ "isDefault": true
+ }
+ },
+ {
+ "isBuildCommand": true,
+ "label": "build debug",
+ "command": "dotnet",
+ "type": "process",
+ "args": [
+ "build",
+ "${workspaceFolder}/Recyclable.Collections.sln",
+ "/property:GenerateFullPaths=true",
+ "/consoleloggerparameters:NoSummary",
+ ],
+ "problemMatcher": "$msCompile",
+ "group": {
+ "kind": "build",
+ "isDefault": false
+ }
+ },
+ {
+ "label": "build release",
+ "command": "dotnet",
+ "type": "process",
+ "args": [
+ "build",
+ "${workspaceFolder}/Recyclable.Collections.sln",
+ "/property:GenerateFullPaths=true",
+ "/consoleloggerparameters:NoSummary",
+ "-c", "Release",
+ ],
+ "problemMatcher": "$msCompile",
+ "group": {
+ "kind": "build",
+ "isDefault": false
+ }
+ },
+ {
+ "label": "publish",
+ "command": "dotnet",
+ "type": "process",
+ "args": [
+ "publish",
+ "${workspaceFolder}/Recyclable.Collections.sln",
+ "/property:GenerateFullPaths=true",
+ "/consoleloggerparameters:NoSummary"
+ ],
+ "problemMatcher": "$msCompile"
+ },
+ {
+ "label": "watch",
+ "command": "dotnet",
+ "type": "process",
+ "args": [
+ "watch",
+ "run",
+ "--project",
+ "${workspaceFolder}/Recyclable.Collections.sln"
+ ],
+ "problemMatcher": "$msCompile"
+ }
+ ]
}
\ No newline at end of file
diff --git a/AGENTS.md b/AGENTS.md
index 3b9641b..7ef3097 100644
--- a/AGENTS.md
+++ b/AGENTS.md
@@ -1,29 +1,29 @@
-# AGENTS
-
-This repository hosts various libraries distributed as NuGet packages. Keep these links up to date so contributors and tools can easily locate them.
-
-Only the .NET SDK **8.0** is available in the execution environment. Use this version when building or running tests.
-
-## Implementation Guidelines
-1. All `*.csproj` files should enable nullable reference types with `enable`.
-1. Implementations should be optimized for maximum performance even if that introduces some code duplication.
-1. Consider applying attributes such as `MethodImplOptions.AggressiveInlining` or faster alternatives to common operations when appropriate. Another would be modulo "%" or division "/" operations, which could be often replaced with faster alternatives, possibly under specific conditions.
-
-## Running Tests
-1. When running `dotnet test`, do **not** pass `--no-build` because that leads to missing assemblies, test failures without logs and other issues.
-1. When running `dotnet test` specify the `--framework` argument matching the SDK available in the environment (currently `net8.0`). If you omit this parameter, the tests will fail running with no logs etc.
-1. The tests run for a very long time, because there are 61_000+ unit tests for all the collections. Set timeout when running them to 15 mis.
-1. All tests must use **xUnit** together with **FluentAssertions**.
-
-## Source Code Formatting Guidelines
-1. Indent code using four spaces or a single tab per level.
-1. Place one blank line after each closing curly brace of a code block, except when several closing braces appear sequentially.
-1. Always use braces for `if` and `else` bodies.
-
-## NuGet packages
-- [Recyclable.Collections](https://github.com/mlemanczyk/Recyclable.Collections)
-- [Recyclable.Collections.Compatibility.List](https://github.com/mlemanczyk/Recyclable.Collections.Compatibility.List)
-- [Recyclable.Collections.Concurrent](https://github.com/mlemanczyk/Recyclable.Collections.Concurrent)
-- [Recyclable.Collections.Linq](https://github.com/mlemanczyk/Recyclable.Collections.Linq)
-- [Recyclable.Collections.Searching](https://github.com/mlemanczyk/Recyclable.Collections.Searching)
-- [Recyclable.Collections.TestData](https://github.com/mlemanczyk/Recyclable.Collections.TestData)
+# AGENTS
+
+This repository hosts various libraries distributed as NuGet packages. Keep these links up to date so contributors and tools can easily locate them.
+
+Only the .NET SDK **8.0** is available in the execution environment. Use this version when building or running tests.
+
+## Implementation Guidelines
+1. All `*.csproj` files should enable nullable reference types with `enable`.
+1. Implementations should be optimized for maximum performance even if that introduces some code duplication.
+1. Consider applying attributes such as `MethodImplOptions.AggressiveInlining` or faster alternatives to common operations when appropriate. Another would be modulo "%" or division "/" operations, which could be often replaced with faster alternatives, possibly under specific conditions.
+
+## Running Tests
+1. When running `dotnet test`, do **not** pass `--no-build` because that leads to missing assemblies, test failures without logs and other issues.
+1. When running `dotnet test` specify the `--framework` argument matching the SDK available in the environment (currently `net8.0`). If you omit this parameter, the tests will fail running with no logs etc.
+1. The tests run for a very long time, because there are 61_000+ unit tests for all the collections. Set timeout when running them to 15 mis.
+1. All tests must use **xUnit** together with **FluentAssertions**.
+
+## Source Code Formatting Guidelines
+1. Indent code using four spaces or a single tab per level.
+1. Place one blank line after each closing curly brace of a code block, except when several closing braces appear sequentially.
+1. Always use braces for `if` and `else` bodies.
+
+## NuGet packages
+- [Recyclable.Collections](https://github.com/mlemanczyk/Recyclable.Collections)
+- [Recyclable.Collections.Compatibility.List](https://github.com/mlemanczyk/Recyclable.Collections.Compatibility.List)
+- [Recyclable.Collections.Concurrent](https://github.com/mlemanczyk/Recyclable.Collections.Concurrent)
+- [Recyclable.Collections.Linq](https://github.com/mlemanczyk/Recyclable.Collections.Linq)
+- [Recyclable.Collections.Searching](https://github.com/mlemanczyk/Recyclable.Collections.Searching)
+- [Recyclable.Collections.TestData](https://github.com/mlemanczyk/Recyclable.Collections.TestData)
diff --git a/LICENSE.md b/LICENSE.md
index b345ef8..34f30fc 100644
--- a/LICENSE.md
+++ b/LICENSE.md
@@ -1,10 +1,10 @@
-# License
-The project & source code is free for educational & personal use. **Any kind** of commercial use requires a donation, as prescribed below.
-
-# Donation requirements for a life-time, commercial use
-* Commercial license is paid one time.
-* It can be obtained by donaiting $10 for each developer seat, using the link provided below. If you hire 2 developers, you need to donate $20 for a life-time, commercial use of this package.
-* Your license stays with you, if your developer moves somewhere else.
-
-# Link for donations
+# License
+The project & source code is free for educational & personal use. **Any kind** of commercial use requires a donation, as prescribed below.
+
+# Donation requirements for a life-time, commercial use
+* Commercial license is paid one time.
+* It can be obtained by donaiting $10 for each developer seat, using the link provided below. If you hire 2 developers, you need to donate $20 for a life-time, commercial use of this package.
+* Your license stays with you, if your developer moves somewhere else.
+
+# Link for donations
[](https://www.buymeacoffee.com/mlemanczyk)
\ No newline at end of file
diff --git a/README.md b/README.md
index 6555228..22aa7ad 100644
--- a/README.md
+++ b/README.md
@@ -1,433 +1,433 @@
-# Recyclable.Collections
-`Recyclable.Collections` project is an open source framework for operating dynamic lists at performance close to raw arrays, but fairly unlimited in size. It aims at providing minimal memory footprint. It implements `IList` interface and is targeted as direct replacements of `List`, `SortableList`, `PriorityQueue` & similar.
-
-## Included
-* `RecyclableList`
-* `RecyclableLongList`
-
-## NuGet packages
-- [Recyclable.Collections](https://github.com/mlemanczyk/Recyclable.Collections)
-- [Recyclable.Collections.Compatibility.List](https://github.com/mlemanczyk/Recyclable.Collections.Compatibility.List)
-- [Recyclable.Collections.Concurrent](https://github.com/mlemanczyk/Recyclable.Collections.Concurrent)
-- [Recyclable.Collections.Linq](https://github.com/mlemanczyk/Recyclable.Collections.Linq)
-- [Recyclable.Collections.Searching](https://github.com/mlemanczyk/Recyclable.Collections.Searching)
-- [Recyclable.Collections.TestData](https://github.com/mlemanczyk/Recyclable.Collections.TestData)
-
-# Milestones
-1. ✅ Create basic classes
- 1. ✅ `RecyclableList`
- 1. ✅ `RecyclableLongList`
- 1. 🅿️ `RecyclableQueue`
- 1. 🅿️ `RecyclableSortedList`
- 1. 🅿️ `RecyclableStack`
- 1. 🅿️ `RecyclableUnorderedList`
-1. ✅ Create basic unit tests
- 1. ✅ `RecyclableList`
- 1. ✅ `RecyclableLongList`
- 1. 🅿️ `RecyclableQueue`
- 1. 🅿️ `RecyclableSortedList`
- 1. 🅿️ `RecyclableStack`
- 1. 🅿️ `RecyclableUnorderedList`
-1. ✅ Optimize `RecyclableList`
- 1. ✅ `Add`
- 1. ✅ `AddRange`
- 1. ✅ when source is `array`
- 1. ✅ when source is `List`
- 1. ✅ when source is `IList`
- 1. ✅ when source is `RecyclableList`
- 1. ✅ when source is `RecyclableLongList`
- 1. ✅ when source is `IEnumerable`
- 1. ✅ when source has non-enumerated count
- 1. ✅ `Clear`
- 1. ✅ `Contains`
- 1. ✅ `CopyTo`
- 1. ✅ `Dispose`
- 1. ✅ `EnsureCapacity`
- 1. ✅ `GetEnumerator`
- 1. ✅ `IndexOf`
- 1. ✅ `Insert`
- 1. ✅ `Remove`
- 1. ✅ `RemoveAt`
- 1. ✅ `Resize`
- 1. ✅ `this[int index]`
-1. ✅ Port `RecyclableList` implementation to `RecyclableLongList`
-1. 👉 Optimize `RecyclableLongList`
- 1. ✅ `Add`
- 1. ✅ `AddRange`
- 1. ✅ when source is `array`
- 1. ✅ when source is `List`
- 1. ✅ when source is `IList`
- 1. ✅ when source is `RecyclableList`
- 1. ✅ when source is `RecyclableLongList`
- 1. ✅ when source is `IEnumerable`
- 1. ✅ when source has non-enumerated count
- 1. ✅ `Clear`
- 1. ✅ `Contains`
- 1. 🅿️ `CopyTo`
- 1. ✅ `Dispose`
- 1. ✅ `EnsureCapacity`
- 1. ✅ `GetEnumerator`
- 1. ✅ `IndexOf`
- 1. ✅ `LongIndexOf`
- 1. ✅ `Insert`
- 1. ✅ `Remove`
- 1. ✅ `RemoveAt(int index)`
- 1. ✅ `RemoveAt(long index)`
- 1. ✅ `RemoveAt`
- 1. ✅ `Resize`
- 1. ✅ `this[int index]`
- 1. ✅ `this[long index]`
- 1. ✅ Rename `RecyclableList` to `RecyclableLongList`
- 1. ✅ Rename `RecyclableArrayList` to `RecyclableList`
- 1. ✅ Fix failing tests
- 1. ✅ Hide not ready classes
- 1. ✅ `RecyclableQueue`
- 1. ✅ `RecyclableSortedList`
- 1. ✅ `RecyclableStack`
- 1. ✅ `RecyclableUnorderedList`
- 1. ✅ Add support for `ReadOnlySpan`
- 1. ✅ Release 0.0.3-alpha
- 1. ✅ Implement `List` interfaces
- 1. ✅ `IList`
- 1. ✅ `ICollection`
- 1. ✅ `IEnumerable`
- 1. ✅ `IEnumerable`
- 1. ✅ `IReadOnlyList`
- 1. ✅ `IReadOnlyCollection`
- 1. ✅ `IList`
- 1. ✅ `ICollection`
- 1. ✅ Implement list versioning to allow data change identification
- 1. ✅ Make sure that `NeedsClearing` is used & items are cleared in
- 1. ✅ `RecyclableList`
- 1. ✅ `Clear`
- 1. ✅ `Dispose`
- 1. ✅ `Remove`
- 1. ✅ `RemoveAt`
- 1. ✅ Properties
- 1. ✅ Non-versioned & Versioned Enumerators
- 1. ✅ `RecyclableListHelpers`
- 1. ✅ `EnsureCapacity`
- 1. ✅ `Resize`
- 1. ✅ `IList` implementation
- 1. ✅ `RecyclableLongList`
- 1. ✅ `Clear`
- 1. ✅ `Dispose`
- 1. ✅ `Remove`
- 1. ✅ `RemoveAt`
- 1. ✅ `RemoveBlock`
- 1. ✅ Properties
- 1. ✅ Non-versioned & Versioned Enumerators
- 1. ✅ `RecyclableLongListHelpers`
- 1. ✅ `CopyFollowingItems`
- 1. ✅ `CopyTo`
- 1. ✅ `EnsureCapacity`
- 1. ✅ `Resize`
- 1. ✅ `RecyclableLongList.IndexOfHelpers`
- 1. ✅ Complete the implementation of `RecyclableLongList`
- 1. ✅ `InsertAt` to allow inserting items anywhere
- 1. ✅ `RemoveAt` to allow removing item at any index
- 1. ✅ Release 0.0.4
- 1. ✅ Extend unit tests
- 1. ✅ `.Add` / `.AddRange` must accept `null` values
- 1. ✅ `.AddRange` must accept empty collections
- 1. ✅ `.Remove` / `.RemoveAt` / `.Clear` / `.Dispose` must clear reference when reference type
- 1. ✅ `.Clear` / `.Dispose` must return arrays to pools
- 1. ✅ `int` / `long` variants of `.Count` / `.LongCount`, `.IndexOf` / `.LongIndexOf`, `.Insert`, `.RemoveAt`, `this[]`
- 1. ✅ Add `.ToRecyclableList` / `.ToRecyclableLongList` variants for all supported collection types
- 1. ✅ `Array`
- 1. ✅ `ICollection`
- 1. ✅ `ICollection`
- 1. ✅ `IEnumerable`
- 1. ✅ `IEnumerable`
- 1. ✅ `IReadOnlyList`
- 1. ✅ `ReadOnlySpan`
- 1. ✅ `RecyclableList`
- 1. ✅ `RecyclableLongList`
- 1. ✅ `Span`
- 1. ✅ `T[]`
- 1. ✅ Release 0.0.5
- 1. ✅ Implement `List` compatibility pack for `RecyclableList`
- 1. ✅ Overflow review
- 1. ✅ Add type casting to `long` for `<<` & `>>` operations, where required
- 1. ✅ Make type castings `checked`, where required
- 1. ✅ Release 0.0.6
- 1. 👉 Implement `List` compatibility pack for `RecyclableLongList`
- 1. 🅿️ Port `RecyclableLongList` optimizations to `RecyclableList`
- 1. `IndexOf` parallelization
- 1. 🅿️ Release 0.0.7
-1. 🅿️ Implement `ILongList` interface
- 1. 🅿️ `RecyclableList`
- 1. 🅿️ `RecyclableLongList`
-1. 🅿️ Implement `RecyclableQueue`
- 1. 🅿️ Port `RecyclableLongList` optimizations to `RecyclableQueue`
- 1. 🅿️ Release 0.0.8
-1. 🅿️ Implement `RecyclableStack`
- 1. 🅿️ Port `RecyclableLongList` optimizations to `RecyclableStack`
- 1. 🅿️ Release 0.0.9
-1. 🅿️ Implement `RecyclableSortedList`
- 1. 🅿️ Port `RecyclableLongList` optimizations to `RecyclableSortedList`
- 1. 🅿️ Release 0.0.10
-1. 🅿️ Implement `RecyclableUnorderedList`
- 1. 🅿️ Port `RecyclableLongList` optimizations to `RecyclableUnorderedList`
- 1. 🅿️ Release 0.0.11
-1. 🅿️ Implement `RecyclableVersionedList`
- 1. 🅿️ Port `RecyclableList` to `RecyclableVersionedList`
- 1. 🅿️ Port `RecyclableLongList` to `RecyclableVersionedLongList`
- 1. 🅿️ Release 0.0.12
-1. 🅿️ Optimize `OneSizeArrayPool`
- 1. 🅿️ Review locks
- 1. 🅿️ Measure multi-threading performance
- 1. 🅿️ Implement memory bucket disposal in high RAM pressure scenario
-1. 🅿️ Optimize `RecyclableCollectionVersionObjectPool`
- 1. 🅿️ Implement custom `ObjectPool`
- 1. 🅿️ Measure multi-threading performance
- 1. 🅿️ Implement memory bucket disposal in high RAM pressure scenario
-1. 🅿️ Review `RecyclableArrayPool`
- 1. 🅿️ Review locks
- 1. 🅿️ Measure multi-threading performance
- 1. 🅿️ Implement array disposal in high RAM pressure scenario
-1. 🅿️ Optimize `MemoryBucket`
- 1. 🅿️ Convert to `struct`, if possible
- 1. 🅿️ Find out if there are better replacements
- 1. 🅿️ Release 0.0.13
-1. 🅿️ Optimize
- 1. 🅿️ `IndexOfSynchronizationContext`
- 1. 🅿️ `IndexOfSynchronizationContextPool`
- 1. 🅿️ `ManualResetEventSlimmer`
- 1. 🅿️ Multi-threading benchmarks
- 1. 🅿️ `ManualResetEventSlimmerPool`
- 1. 🅿️ Multi-threading benchmarks
- 1. 🅿️ `SpinLockSlimmer`
- 1. 🅿️ Multi-threading benchmarks
- 1. 🅿️ Remove range operators, where possible
-1. 🅿️ Release 0.0.14
-1. 🅿️ Extend unit tests
- 1. 🅿️ `RecyclableLongListExtensions.CopyTo`
- 1. 🅿️ `RecyclableLongList` cases for large items count (>`int.MaxValue`)
- 1. 🅿️ Pools
- 1. 🅿️ Multi-threading
- 1. 🅿️ Add comparison tests vs `T[]` / `List` equivalents
- 1. 🅿️ Add test cases for indexes beyond items count
- 1. 🅿️ Cover border cases
- 1. 🅿️ Non-existing items in `.Contains...()`, `.Exists...()`, `.Find...()`, `.IndexOf...()`, `.Last...()`
- 1. 🅿️ Duplicated items in `.Contains...()`, `.Exists...()`, `.Find...()`, `.IndexOf...()`, `.Last...()`
- 1. 🅿️ Append test data in reversed order in `.AddRange()`, `.InsertRange()` and similar tests
- 1. 🅿️ Switch tests to use Source / Target data variants in `.AddRange()`, `.InsertRange()` and similar tests
-1. 🅿️ Cleanup
- 1. 🅿️ Replace `LastBlockWithData` property with `_lastBlockWithData` field
- 1. 🅿️ Replace all internal properties refs with fields, where possible
- 1. ✅ `RecyclableLongListExtensions`
- 1. ✅ `ListExtensions`
- 1. 🅿️ `MathUtils`
- 1. 🅿️ Resolve TODOs
- 1. 🅿️ Remove obsolete methods
- 1. 🅿️ Add`RecyclableLongListHelpers.Enumerate` to benchmarks
- 1. 🅿️ Review all classes & add `volatile`, where needed
- 1. 🅿️ Remove `expectedItemsCount` parameter from `RecyclableLongList`'s constructor
- 1. 🅿️ Remove `array` slicing in favor for indexing, like in `RecyclableCompatibilityListExtensions`
-1. 🅿️ Release 0.0.15
-1. 🅿️ Optimize
- 1. 🅿️ `ListExtensions`
- 1. 🅿️ `MathUtils`
- 1. 🅿️ `SystemRandomNumberGenerator`
- 1. 🅿️ `RecyclableLongListExtensions`
- 1. 🅿️ Memory release in pools to utilize GC events in case of memory pressure
-1. 🅿️ Release 0.0.16
-1. ✅ Review and remove warnings & hints
- 1. ✅ Warnings
- 1. ✅ Hints
-1. Documentation
- 1. 🅿️ Document the most efficient iteration over array collections
- 1. 🅿️ Document the most efficient iteration over blocked collections
- 1. 🅿️ Document differences in behavior
- 1. 🅿️ Document other specifics
-1. 🅿️ Release 1.0.0
-1. 🅿️ Implement source code generators
- 1. 🅿️ Add attributes
- 1. 🅿️ `GeneratorBaseClassAttribute` for marking base class used for generation
- 1. 🅿️ `VersionedAttribute` for marking classes as versioned
- 1. 🅿️ `IncVersionAttribute` for marking methods & setters as resulting in version increase
- 1. 🅿️ Implement source code generator
- 1. 🅿️ Generate partial class for classes marked with `GeneratorBaseClassAttribute`
- 1. 🅿️ Add support for fields
- 1. 🅿️ Add support for properties
- 1. 🅿️ Add support for methods
- 1. 🅿️ Add support for constructor
- 1. 🅿️ Skip base fields, methods, properties etc. when they're overridden in the child class
-1. 🅿️ Add support for `ulong` indexing
- 1. 🅿️ Convert `_memoryBlocks` to `Array` to allow `ulong` lengths
- 1. 🅿️ Convert block indexes from `int` to `ulong` or `long`
-1. 🅿️ Optimize
- 1. 🅿️ `RecyclableLongList.Resize`
- 1. 🅿️ `RecyclableLongList.CopyTo`
- 1. 🅿️ Check if we can benefit from Sse2 in `.IndexOf`/`.Contains` methods as given in [MS blog](https://devblogs.microsoft.com/dotnet/hardware-intrinsics-in-net-core/).
- 1. 🅿️ Memory pools
- 1. 🅿️ `OneSizeArrayPool`
- 1. 🅿️ `RecyclableArrayPool`
-1. 🅿️ Add support for `ICollection` interface in `.AddRange` & `constructor`
-1. 🅿️ Final optimizations
- 1. 🅿️ Replace `Math` class usages with `if` statements
- 1. 🅿️ Replace `a - b > 0` & `a - b < 0` comparisons with `a > b` & `a < b`
- 1. 🅿️ Replace `a + b > 0` & `a + b < 0` comparisons with `a > b` & `a < b`
- 1. 🅿️ Replace `a / b` & `a * b` calculations with equivalents, where possible
- 1. 🅿️ Replace virtual calls with static calls
- 1. 🅿️ Separate `++number`, `number++`, `--number` & `number--` operations to their own lines (they add extra variable)
- 1. 🅿️ Replace `blockSize` sums by powers of 2, minus 1
- 1. 🅿️ Remove type castings, if possible
- 1. 🅿️ Convert generic methods to non-generic
- 1. 🅿️ Replace integer comparisons with comparisons to 0 / 1, if possible
-1. 🅿️ Release 2.0.0
-
-# Characteristics of the classes
-
-## Common
-* All classes implement `IDisposable` interface & SHOULD be disposed after use. That's to return block arrays taken from the shared pool. It may be foreseen as an issue for replacement in existing code, which obviously is missing `using` clause. But considering that `Dispose` will be called by `GC` anyway, it should cause issues in specific scenarios, only. In either case the fix is one-word addition of `using`.
-* Memory blocks are created in 2 ways, depending on `blockSize` value
- * when `blockSize < 128` ⇨ blocks are created as regular `arrays`.
- * when `blockSize >= 128` ⇨ blocks are taken from and returned to `ArrayPool.Shared`, when blocks are removed.
- * maximum `blockSize` value is `2_147_483_591`, which corresponds more or less to the maximum array size.
- * `blockSize` MUST be a power of 2. It will be rounded up to the closest power of 2, if needed. That is due to high performance gain on some operations, like the calculation of item index in a block.
-* Array pools are shared between the same `T` type. I.e. `List` will use a different pool from `List` and so on. For high concurrency environments you may want to provide your own pools, when this feature becomes available in the upcoming releases.
-* Trying to access `this[int index]`, `this[long index]`, `Count`, `LongCount` etc. when `Capacity == 0` will raise `NullReferenceException`. This is by design to remove all non-critical code from the constructor.
-* ⚠️ The default enumerators don't check if the collection was modified. That's by design due to high performance hit of the check. That should be fine in most use-cases. If you need to check for modifications, you're welcomed to use `.GetVersionedEnumerator()` / `IRecyclableVersionedXxxList` type-casting, e.g. in `foreach` loops.
- ```csharp
- foreach (var item in (IRecyclableVersionedList)recyclableList)
- {
- ...
- ...
- ...
- }
-
- foreach (var item in (IRecyclableVersionedLongList)recyclableLongList)
- {
- ...
- ...
- ...
- }
- ```
-* ⚠️ The state of the default enumerators before the first & after the last call to `.MoveNext()` is undefined, but no exception is raised. That's by design due to high performance hit of the checks. This behavior is compatible with `foreach` loops, which will never access `.Current` property
- * when the collection is empty, or
- * when `.MoveNext()` returned `false`, after reaching the end of the collection.
-
-* ⚠️ If you decide to use `.GetEnumerator()` / `.GetVersionedEnumerator()`, instead of relying on `foreach` loops
- * you MUST ensure that you always respect the result of `.MoveNext()` call, and
- * you MUST NOT access `.Current` property before calling `.MoveNext()` or after reaching the end of the collection.
-
- \
- **Failing to do so WILL result in unpredictable behavior.**
-
- ### [Benchmark results](https://github.com/mlemanczyk/Recyclable.Collections/blob/main/Recyclable.Collections.Benchmarks/Results/Benchmarks.md)
-
-## `RecyclableList`
-* Range: `int`
-* Interfaces: `IList`, `IEnumerable`, `IDisposable`\
-\
-This is the direct equivalent of `List` class, except that the arrays are taken from the shared pool, instead of directly being allocated. It proves to out perform `List` & the standard arrays in certain operations and is fairly close in others. But they may perform worse in certain scenarios. If you're interested in details, please refer to benchmarks.
-
-## `RecyclableLongList`, `RecyclableSortableList`, `RecyclableQueue`, `RecyclableStack`
-* Range: `long`
-* Interfaces: `IList`, `ILongList`, `IEnumerable`, `IDisposable`
-* All classes provide large storage capabilities, in practice limited only by the memory available in your system.
-* All data is stored in blocks, with the provided `int blockSize` or the default, currently being `10,240` items in each block. It's recommended to use smaller numbers, if you foresee storing low no. of items on the list.
-* There is no memory copying to increase the capacity of the recyclable classes, unless the no. of items exceeds the no. of allocated blocks. In that case, a new array of blocks is created to accommodate . If more capacity is needed, a new memory block is allocate & added to the internal list of blocks. This is the only list that may re-allocate memory block & copy their content to grow. That shouldn't be an issue considering limited no. of blocks stored by each class in practical scenarios. Currently I'm not planning any works around that. Shall there be a need to eliminate it, you're welcomed to file a PR with the proposed changes.
-* ⚠️ `IndexOf` will automatically switch to parallel search mode. Collections bigger than (currently) 850_000 items will be scanned using parallelization. In either case it'll return the index of the first matching item. This note also applies to `Contains`, because it internally uses `IndexOf`. The value of 850_000 may become configurable in the future, unless it proves to result in much worse performance.
-
- The parallelization utilizes default `Task` scheduling, resulting in non-deterministic order in which search tasks are executed. In most cases it resulted in significant performance improvements. Below you can find the benchmarks for various item counts.
-
- As `RecyclableLongList` is foreseen for use-cases with big data, you should automatically benefit from it in many use-cases.
-
- ### [Benchmark Results](https://github.com/mlemanczyk/Recyclable.Collections/blob/main/Recyclable.Collections.Benchmarks/Results/Benchmarks.md)
-
-# Architecture Decisions
-The architecture of the classes included in this project is driven primarily by performance & memory footprints. The following decisions were made to support it.
-
-## Code duplication
-There is high level of code duplication in each of the classes. When you look at them, you will see they are alike & some of the code could be extracted to extension methods. It has been done & has proven to perform worse. For this reason, properties & methods expected to be on the hot-path, duplicate much of the code to get the most out of it.
-
-## Common base - `ILongList`
-Having a common base class for all the classes looks very attractive. But it is also proved to perform worse, if you start making properties & methods virtual & there are subsequent calls to `base`. For this reason, each of the classes is the root class & there are hardly any virtual methods & properties. All classes are meant to be `final`, but I've not marked them as `sealed`. If you feel that you'd benefit from it, you're welcomed to inherit from them. The protected stuff is there for your use.
-
-If you desire to have a common base for calls, each of the classes implements `IList` & `ILongList` interfaces. `ILongList` is a new interface, made alike `IList`, but unlocking full support for `long` indexing & use. Considering the characteristics of the classes I feel that the generic name is justified, instead of `IRecyclableList` what you could expect.
-
-## Protection against incorrect use & state
-Having protection against invalid state of the object is an important part of software engineering. The classes included in this project provide the same level of protection as the regular `array` & `List` class. They will raise exceptions when invalid index is given. But there is no additional protection that the content & state of the objects internally used by these classes are valid. You can break them, if you want to.
-
-This decision is driven by performance measures. Considering wide use of the lists on the hot-paths, each additional check & operation starts counting. I've decided to eliminate all the checks for the sake of performance. If you feel that you need additional protection, feel free to inherit or reuse any of the provided classes to provide that.
-
-## `this[int index]`, `Count`, `IndexOf(T item)` etc. may overflow, but...
-All the classes included in this package support `long` indexing and addressing. The `LongCount` property will always provide the total no. of items stored on the list. Since `Count` is just `LongCount` type-casted to `int`, its value may overflow.
-
-But `List` addressing is kind of currently limited to `int` ranges anyway in practical scenarios. As such `Count` overflowing shouldn't be an issue when using the classes with existing code. If you use `Count` in your loops, it's recommended to replace it with `LongCount`, tough. You don't need to make any changes in `foreach` or other iterator loops. They are expected to transparently use the new classes & yield all items, beyond `int.MaxValue` range.
-
-This is by design, for the best performance. Initially there have been checks in place to prevent overflowing & return `int.MaxValue` instead, but they proved to slow down the operations. Considering low risk for existing code, I've decided to take it out.
-
-If you foresee the overflowing as an issue, you're welcomed to propose an improvement & file a PR with proposed solution.
-
-# Auto-properties, new language features & code style
-When you look at the code you may note, that it looks like in early c# days. Where the new language features yield the same or better performance, they are & will be used.
-
-However, many of the new language features have proved to provide worse performance at some point in my testing. It includes auto-properties, for which I could see getters & setters generated in IL, instead of fields. Because all the classes are expected to be on the hot-paths, I've eliminated most of them.
-
-Similarly, you will find places in code with hints or warnings disabled. The decision was always driven by performance measures. The use case & business logic was carefully reviewed to ensure it's safe to take shortcuts, before making the change. If you run into failing scenario, please feel free to create a work item against it and/or file a PR to fix it.
-
-Finally, you'll find places with code commented out. That's to easily track what has been tried & what proved to perform worse.
-
-At any time, if you know & can show in your benchmarks that the code can be simplified without impacting the performance, feel free to file a PR with proposed changes. Please include benchmark results from your testing to speed up things.
-
-# Thread Safety
-The `public static` members of the classes are thread safe. Any instance members are not guaranteed to be thread safe. You need to implement locking mechanism to safely use the classes in a multi-threading environment.
-
-# Use
-All the classes included in this package are meant to be direct replacements of their corresponding system classes.
-* `IList` ⇨ `ILongList`
-* `List` ⇨ `RecyclableLongList`
-* `Queue` ⇨ `RecyclableQueue`
-* `PriorityQueue` ⇨ `RecyclableSortedList`
-* `SortedList` ⇨ `RecyclableSortedList`
-* `Stack` ⇨ `RecyclableStack`
-
-Examples of each of the above classes are provided below. Please refer automated tests for more.
-
-## `RecyclableList`
-It's the closest equivalent to `List` in regards to functionality. It supports items' removal & delivers the best performance in most scenarios. But it's limited to `int` range, tough. If you find that acceptable, my recommendation is to use this class as the direct replacement for `List`.
-
-Do note, that it implements `ILongList` interface, too. This is to allow having common code base regardless, if you use the basic `RecyclableList` or it's `long`-range version - `RecyclableLongList`. By doing that you can switch between them with highly limited changes in code.
-
-## `RecyclableLongList`
-
-```CSharp
-public void RecyclableListExample()
-{
- int[] testNumbers = new[] { 1, 2, 2, 3 };
-
- // Create
- using var list = new RecyclableLongList();
-
- // Add items
- foreach (var index in testNumbers)
- {
- list.Add(index);
- }
-
- foreach (var item in list)
- {
- Console.WriteLine(item);
- }
-
- // This will iterate over this[long index]
- for (var itemIdx = 0; itemIdx <= list.LongCount; itemIdx++)
- {
- Console.WriteLine(list[itemIdx]);
- }
-
- // This will iterate over this[int index] and may overflow if there are > int.MaxValue no. of items on the list. See: Architecture Decisions
- for (var itemIdx = 0; itemIdx <= list.LongCount; itemIdx++)
- {
- Console.WriteLine(list[itemIdx]);
- }
-
- list.Clear();
-}
-```
-
-### [Benchmark results](https://github.com/mlemanczyk/Recyclable.Collections/blob/main/Recyclable.Collections.Benchmarks/Results/Benchmarks.md)
+# Recyclable.Collections
+`Recyclable.Collections` project is an open source framework for operating dynamic lists at performance close to raw arrays, but fairly unlimited in size. It aims at providing minimal memory footprint. It implements `IList` interface and is targeted as direct replacements of `List`, `SortableList`, `PriorityQueue` & similar.
+
+## Included
+* `RecyclableList`
+* `RecyclableLongList`
+
+## NuGet packages
+- [Recyclable.Collections](https://github.com/mlemanczyk/Recyclable.Collections)
+- [Recyclable.Collections.Compatibility.List](https://github.com/mlemanczyk/Recyclable.Collections.Compatibility.List)
+- [Recyclable.Collections.Concurrent](https://github.com/mlemanczyk/Recyclable.Collections.Concurrent)
+- [Recyclable.Collections.Linq](https://github.com/mlemanczyk/Recyclable.Collections.Linq)
+- [Recyclable.Collections.Searching](https://github.com/mlemanczyk/Recyclable.Collections.Searching)
+- [Recyclable.Collections.TestData](https://github.com/mlemanczyk/Recyclable.Collections.TestData)
+
+# Milestones
+1. ✅ Create basic classes
+ 1. ✅ `RecyclableList`
+ 1. ✅ `RecyclableLongList`
+ 1. 🅿️ `RecyclableQueue`
+ 1. 🅿️ `RecyclableSortedList`
+ 1. 🅿️ `RecyclableStack`
+ 1. 🅿️ `RecyclableUnorderedList`
+1. ✅ Create basic unit tests
+ 1. ✅ `RecyclableList`
+ 1. ✅ `RecyclableLongList`
+ 1. 🅿️ `RecyclableQueue`
+ 1. 🅿️ `RecyclableSortedList`
+ 1. 🅿️ `RecyclableStack`
+ 1. 🅿️ `RecyclableUnorderedList`
+1. ✅ Optimize `RecyclableList`
+ 1. ✅ `Add`
+ 1. ✅ `AddRange`
+ 1. ✅ when source is `array`
+ 1. ✅ when source is `List`
+ 1. ✅ when source is `IList`
+ 1. ✅ when source is `RecyclableList`
+ 1. ✅ when source is `RecyclableLongList`
+ 1. ✅ when source is `IEnumerable`
+ 1. ✅ when source has non-enumerated count
+ 1. ✅ `Clear`
+ 1. ✅ `Contains`
+ 1. ✅ `CopyTo`
+ 1. ✅ `Dispose`
+ 1. ✅ `EnsureCapacity`
+ 1. ✅ `GetEnumerator`
+ 1. ✅ `IndexOf`
+ 1. ✅ `Insert`
+ 1. ✅ `Remove`
+ 1. ✅ `RemoveAt`
+ 1. ✅ `Resize`
+ 1. ✅ `this[int index]`
+1. ✅ Port `RecyclableList` implementation to `RecyclableLongList`
+1. 👉 Optimize `RecyclableLongList`
+ 1. ✅ `Add`
+ 1. ✅ `AddRange`
+ 1. ✅ when source is `array`
+ 1. ✅ when source is `List`
+ 1. ✅ when source is `IList`
+ 1. ✅ when source is `RecyclableList`
+ 1. ✅ when source is `RecyclableLongList`
+ 1. ✅ when source is `IEnumerable`
+ 1. ✅ when source has non-enumerated count
+ 1. ✅ `Clear`
+ 1. ✅ `Contains`
+ 1. 🅿️ `CopyTo`
+ 1. ✅ `Dispose`
+ 1. ✅ `EnsureCapacity`
+ 1. ✅ `GetEnumerator`
+ 1. ✅ `IndexOf`
+ 1. ✅ `LongIndexOf`
+ 1. ✅ `Insert`
+ 1. ✅ `Remove`
+ 1. ✅ `RemoveAt(int index)`
+ 1. ✅ `RemoveAt(long index)`
+ 1. ✅ `RemoveAt`
+ 1. ✅ `Resize`
+ 1. ✅ `this[int index]`
+ 1. ✅ `this[long index]`
+ 1. ✅ Rename `RecyclableList` to `RecyclableLongList`
+ 1. ✅ Rename `RecyclableArrayList` to `RecyclableList`
+ 1. ✅ Fix failing tests
+ 1. ✅ Hide not ready classes
+ 1. ✅ `RecyclableQueue`
+ 1. ✅ `RecyclableSortedList`
+ 1. ✅ `RecyclableStack`
+ 1. ✅ `RecyclableUnorderedList`
+ 1. ✅ Add support for `ReadOnlySpan`
+ 1. ✅ Release 0.0.3-alpha
+ 1. ✅ Implement `List` interfaces
+ 1. ✅ `IList`
+ 1. ✅ `ICollection`
+ 1. ✅ `IEnumerable`
+ 1. ✅ `IEnumerable`
+ 1. ✅ `IReadOnlyList`
+ 1. ✅ `IReadOnlyCollection`
+ 1. ✅ `IList`
+ 1. ✅ `ICollection`
+ 1. ✅ Implement list versioning to allow data change identification
+ 1. ✅ Make sure that `NeedsClearing` is used & items are cleared in
+ 1. ✅ `RecyclableList`
+ 1. ✅ `Clear`
+ 1. ✅ `Dispose`
+ 1. ✅ `Remove`
+ 1. ✅ `RemoveAt`
+ 1. ✅ Properties
+ 1. ✅ Non-versioned & Versioned Enumerators
+ 1. ✅ `RecyclableListHelpers`
+ 1. ✅ `EnsureCapacity`
+ 1. ✅ `Resize`
+ 1. ✅ `IList` implementation
+ 1. ✅ `RecyclableLongList`
+ 1. ✅ `Clear`
+ 1. ✅ `Dispose`
+ 1. ✅ `Remove`
+ 1. ✅ `RemoveAt`
+ 1. ✅ `RemoveBlock`
+ 1. ✅ Properties
+ 1. ✅ Non-versioned & Versioned Enumerators
+ 1. ✅ `RecyclableLongListHelpers`
+ 1. ✅ `CopyFollowingItems`
+ 1. ✅ `CopyTo`
+ 1. ✅ `EnsureCapacity`
+ 1. ✅ `Resize`
+ 1. ✅ `RecyclableLongList.IndexOfHelpers`
+ 1. ✅ Complete the implementation of `RecyclableLongList`
+ 1. ✅ `InsertAt` to allow inserting items anywhere
+ 1. ✅ `RemoveAt` to allow removing item at any index
+ 1. ✅ Release 0.0.4
+ 1. ✅ Extend unit tests
+ 1. ✅ `.Add` / `.AddRange` must accept `null` values
+ 1. ✅ `.AddRange` must accept empty collections
+ 1. ✅ `.Remove` / `.RemoveAt` / `.Clear` / `.Dispose` must clear reference when reference type
+ 1. ✅ `.Clear` / `.Dispose` must return arrays to pools
+ 1. ✅ `int` / `long` variants of `.Count` / `.LongCount`, `.IndexOf` / `.LongIndexOf`, `.Insert`, `.RemoveAt`, `this[]`
+ 1. ✅ Add `.ToRecyclableList` / `.ToRecyclableLongList` variants for all supported collection types
+ 1. ✅ `Array`
+ 1. ✅ `ICollection`
+ 1. ✅ `ICollection`
+ 1. ✅ `IEnumerable`
+ 1. ✅ `IEnumerable`
+ 1. ✅ `IReadOnlyList`
+ 1. ✅ `ReadOnlySpan`
+ 1. ✅ `RecyclableList`
+ 1. ✅ `RecyclableLongList`
+ 1. ✅ `Span`
+ 1. ✅ `T[]`
+ 1. ✅ Release 0.0.5
+ 1. ✅ Implement `List` compatibility pack for `RecyclableList`
+ 1. ✅ Overflow review
+ 1. ✅ Add type casting to `long` for `<<` & `>>` operations, where required
+ 1. ✅ Make type castings `checked`, where required
+ 1. ✅ Release 0.0.6
+ 1. 👉 Implement `List` compatibility pack for `RecyclableLongList`
+ 1. 🅿️ Port `RecyclableLongList` optimizations to `RecyclableList`
+ 1. `IndexOf` parallelization
+ 1. 🅿️ Release 0.0.7
+1. 🅿️ Implement `ILongList` interface
+ 1. 🅿️ `RecyclableList`
+ 1. 🅿️ `RecyclableLongList`
+1. 🅿️ Implement `RecyclableQueue`
+ 1. 🅿️ Port `RecyclableLongList` optimizations to `RecyclableQueue`
+ 1. 🅿️ Release 0.0.8
+1. 🅿️ Implement `RecyclableStack`
+ 1. 🅿️ Port `RecyclableLongList` optimizations to `RecyclableStack`
+ 1. 🅿️ Release 0.0.9
+1. 🅿️ Implement `RecyclableSortedList`
+ 1. 🅿️ Port `RecyclableLongList` optimizations to `RecyclableSortedList`
+ 1. 🅿️ Release 0.0.10
+1. 🅿️ Implement `RecyclableUnorderedList`
+ 1. 🅿️ Port `RecyclableLongList` optimizations to `RecyclableUnorderedList`
+ 1. 🅿️ Release 0.0.11
+1. 🅿️ Implement `RecyclableVersionedList`
+ 1. 🅿️ Port `RecyclableList` to `RecyclableVersionedList`
+ 1. 🅿️ Port `RecyclableLongList` to `RecyclableVersionedLongList`
+ 1. 🅿️ Release 0.0.12
+1. 🅿️ Optimize `OneSizeArrayPool`
+ 1. 🅿️ Review locks
+ 1. 🅿️ Measure multi-threading performance
+ 1. 🅿️ Implement memory bucket disposal in high RAM pressure scenario
+1. 🅿️ Optimize `RecyclableCollectionVersionObjectPool`
+ 1. 🅿️ Implement custom `ObjectPool`
+ 1. 🅿️ Measure multi-threading performance
+ 1. 🅿️ Implement memory bucket disposal in high RAM pressure scenario
+1. 🅿️ Review `RecyclableArrayPool`
+ 1. 🅿️ Review locks
+ 1. 🅿️ Measure multi-threading performance
+ 1. 🅿️ Implement array disposal in high RAM pressure scenario
+1. 🅿️ Optimize `MemoryBucket`
+ 1. 🅿️ Convert to `struct`, if possible
+ 1. 🅿️ Find out if there are better replacements
+ 1. 🅿️ Release 0.0.13
+1. 🅿️ Optimize
+ 1. 🅿️ `IndexOfSynchronizationContext`
+ 1. 🅿️ `IndexOfSynchronizationContextPool`
+ 1. 🅿️ `ManualResetEventSlimmer`
+ 1. 🅿️ Multi-threading benchmarks
+ 1. 🅿️ `ManualResetEventSlimmerPool`
+ 1. 🅿️ Multi-threading benchmarks
+ 1. 🅿️ `SpinLockSlimmer`
+ 1. 🅿️ Multi-threading benchmarks
+ 1. 🅿️ Remove range operators, where possible
+1. 🅿️ Release 0.0.14
+1. 🅿️ Extend unit tests
+ 1. 🅿️ `RecyclableLongListExtensions.CopyTo`
+ 1. 🅿️ `RecyclableLongList` cases for large items count (>`int.MaxValue`)
+ 1. 🅿️ Pools
+ 1. 🅿️ Multi-threading
+ 1. 🅿️ Add comparison tests vs `T[]` / `List` equivalents
+ 1. 🅿️ Add test cases for indexes beyond items count
+ 1. 🅿️ Cover border cases
+ 1. 🅿️ Non-existing items in `.Contains...()`, `.Exists...()`, `.Find...()`, `.IndexOf...()`, `.Last...()`
+ 1. 🅿️ Duplicated items in `.Contains...()`, `.Exists...()`, `.Find...()`, `.IndexOf...()`, `.Last...()`
+ 1. 🅿️ Append test data in reversed order in `.AddRange()`, `.InsertRange()` and similar tests
+ 1. 🅿️ Switch tests to use Source / Target data variants in `.AddRange()`, `.InsertRange()` and similar tests
+1. 🅿️ Cleanup
+ 1. 🅿️ Replace `LastBlockWithData` property with `_lastBlockWithData` field
+ 1. 🅿️ Replace all internal properties refs with fields, where possible
+ 1. ✅ `RecyclableLongListExtensions`
+ 1. ✅ `ListExtensions`
+ 1. 🅿️ `MathUtils`
+ 1. 🅿️ Resolve TODOs
+ 1. 🅿️ Remove obsolete methods
+ 1. 🅿️ Add`RecyclableLongListHelpers.Enumerate` to benchmarks
+ 1. 🅿️ Review all classes & add `volatile`, where needed
+ 1. 🅿️ Remove `expectedItemsCount` parameter from `RecyclableLongList`'s constructor
+ 1. 🅿️ Remove `array` slicing in favor for indexing, like in `RecyclableCompatibilityListExtensions`
+1. 🅿️ Release 0.0.15
+1. 🅿️ Optimize
+ 1. 🅿️ `ListExtensions`
+ 1. 🅿️ `MathUtils`
+ 1. 🅿️ `SystemRandomNumberGenerator`
+ 1. 🅿️ `RecyclableLongListExtensions`
+ 1. 🅿️ Memory release in pools to utilize GC events in case of memory pressure
+1. 🅿️ Release 0.0.16
+1. ✅ Review and remove warnings & hints
+ 1. ✅ Warnings
+ 1. ✅ Hints
+1. Documentation
+ 1. 🅿️ Document the most efficient iteration over array collections
+ 1. 🅿️ Document the most efficient iteration over blocked collections
+ 1. 🅿️ Document differences in behavior
+ 1. 🅿️ Document other specifics
+1. 🅿️ Release 1.0.0
+1. 🅿️ Implement source code generators
+ 1. 🅿️ Add attributes
+ 1. 🅿️ `GeneratorBaseClassAttribute` for marking base class used for generation
+ 1. 🅿️ `VersionedAttribute` for marking classes as versioned
+ 1. 🅿️ `IncVersionAttribute` for marking methods & setters as resulting in version increase
+ 1. 🅿️ Implement source code generator
+ 1. 🅿️ Generate partial class for classes marked with `GeneratorBaseClassAttribute`
+ 1. 🅿️ Add support for fields
+ 1. 🅿️ Add support for properties
+ 1. 🅿️ Add support for methods
+ 1. 🅿️ Add support for constructor
+ 1. 🅿️ Skip base fields, methods, properties etc. when they're overridden in the child class
+1. 🅿️ Add support for `ulong` indexing
+ 1. 🅿️ Convert `_memoryBlocks` to `Array` to allow `ulong` lengths
+ 1. 🅿️ Convert block indexes from `int` to `ulong` or `long`
+1. 🅿️ Optimize
+ 1. 🅿️ `RecyclableLongList.Resize`
+ 1. 🅿️ `RecyclableLongList.CopyTo`
+ 1. 🅿️ Check if we can benefit from Sse2 in `.IndexOf`/`.Contains` methods as given in [MS blog](https://devblogs.microsoft.com/dotnet/hardware-intrinsics-in-net-core/).
+ 1. 🅿️ Memory pools
+ 1. 🅿️ `OneSizeArrayPool`
+ 1. 🅿️ `RecyclableArrayPool`
+1. 🅿️ Add support for `ICollection` interface in `.AddRange` & `constructor`
+1. 🅿️ Final optimizations
+ 1. 🅿️ Replace `Math` class usages with `if` statements
+ 1. 🅿️ Replace `a - b > 0` & `a - b < 0` comparisons with `a > b` & `a < b`
+ 1. 🅿️ Replace `a + b > 0` & `a + b < 0` comparisons with `a > b` & `a < b`
+ 1. 🅿️ Replace `a / b` & `a * b` calculations with equivalents, where possible
+ 1. 🅿️ Replace virtual calls with static calls
+ 1. 🅿️ Separate `++number`, `number++`, `--number` & `number--` operations to their own lines (they add extra variable)
+ 1. 🅿️ Replace `blockSize` sums by powers of 2, minus 1
+ 1. 🅿️ Remove type castings, if possible
+ 1. 🅿️ Convert generic methods to non-generic
+ 1. 🅿️ Replace integer comparisons with comparisons to 0 / 1, if possible
+1. 🅿️ Release 2.0.0
+
+# Characteristics of the classes
+
+## Common
+* All classes implement `IDisposable` interface & SHOULD be disposed after use. That's to return block arrays taken from the shared pool. It may be foreseen as an issue for replacement in existing code, which obviously is missing `using` clause. But considering that `Dispose` will be called by `GC` anyway, it should cause issues in specific scenarios, only. In either case the fix is one-word addition of `using`.
+* Memory blocks are created in 2 ways, depending on `blockSize` value
+ * when `blockSize < 128` ⇨ blocks are created as regular `arrays`.
+ * when `blockSize >= 128` ⇨ blocks are taken from and returned to `ArrayPool.Shared`, when blocks are removed.
+ * maximum `blockSize` value is `2_147_483_591`, which corresponds more or less to the maximum array size.
+ * `blockSize` MUST be a power of 2. It will be rounded up to the closest power of 2, if needed. That is due to high performance gain on some operations, like the calculation of item index in a block.
+* Array pools are shared between the same `T` type. I.e. `List` will use a different pool from `List` and so on. For high concurrency environments you may want to provide your own pools, when this feature becomes available in the upcoming releases.
+* Trying to access `this[int index]`, `this[long index]`, `Count`, `LongCount` etc. when `Capacity == 0` will raise `NullReferenceException`. This is by design to remove all non-critical code from the constructor.
+* ⚠️ The default enumerators don't check if the collection was modified. That's by design due to high performance hit of the check. That should be fine in most use-cases. If you need to check for modifications, you're welcomed to use `.GetVersionedEnumerator()` / `IRecyclableVersionedXxxList` type-casting, e.g. in `foreach` loops.
+ ```csharp
+ foreach (var item in (IRecyclableVersionedList)recyclableList)
+ {
+ ...
+ ...
+ ...
+ }
+
+ foreach (var item in (IRecyclableVersionedLongList)recyclableLongList)
+ {
+ ...
+ ...
+ ...
+ }
+ ```
+* ⚠️ The state of the default enumerators before the first & after the last call to `.MoveNext()` is undefined, but no exception is raised. That's by design due to high performance hit of the checks. This behavior is compatible with `foreach` loops, which will never access `.Current` property
+ * when the collection is empty, or
+ * when `.MoveNext()` returned `false`, after reaching the end of the collection.
+
+* ⚠️ If you decide to use `.GetEnumerator()` / `.GetVersionedEnumerator()`, instead of relying on `foreach` loops
+ * you MUST ensure that you always respect the result of `.MoveNext()` call, and
+ * you MUST NOT access `.Current` property before calling `.MoveNext()` or after reaching the end of the collection.
+
+ \
+ **Failing to do so WILL result in unpredictable behavior.**
+
+ ### [Benchmark results](https://github.com/mlemanczyk/Recyclable.Collections/blob/main/Recyclable.Collections.Benchmarks/Results/Benchmarks.md)
+
+## `RecyclableList`
+* Range: `int`
+* Interfaces: `IList`, `IEnumerable`, `IDisposable`\
+\
+This is the direct equivalent of `List` class, except that the arrays are taken from the shared pool, instead of directly being allocated. It proves to out perform `List` & the standard arrays in certain operations and is fairly close in others. But they may perform worse in certain scenarios. If you're interested in details, please refer to benchmarks.
+
+## `RecyclableLongList`, `RecyclableSortableList`, `RecyclableQueue`, `RecyclableStack`
+* Range: `long`
+* Interfaces: `IList`, `ILongList`, `IEnumerable`, `IDisposable`
+* All classes provide large storage capabilities, in practice limited only by the memory available in your system.
+* All data is stored in blocks, with the provided `int blockSize` or the default, currently being `10,240` items in each block. It's recommended to use smaller numbers, if you foresee storing low no. of items on the list.
+* There is no memory copying to increase the capacity of the recyclable classes, unless the no. of items exceeds the no. of allocated blocks. In that case, a new array of blocks is created to accommodate . If more capacity is needed, a new memory block is allocate & added to the internal list of blocks. This is the only list that may re-allocate memory block & copy their content to grow. That shouldn't be an issue considering limited no. of blocks stored by each class in practical scenarios. Currently I'm not planning any works around that. Shall there be a need to eliminate it, you're welcomed to file a PR with the proposed changes.
+* ⚠️ `IndexOf` will automatically switch to parallel search mode. Collections bigger than (currently) 850_000 items will be scanned using parallelization. In either case it'll return the index of the first matching item. This note also applies to `Contains`, because it internally uses `IndexOf`. The value of 850_000 may become configurable in the future, unless it proves to result in much worse performance.
+
+ The parallelization utilizes default `Task` scheduling, resulting in non-deterministic order in which search tasks are executed. In most cases it resulted in significant performance improvements. Below you can find the benchmarks for various item counts.
+
+ As `RecyclableLongList` is foreseen for use-cases with big data, you should automatically benefit from it in many use-cases.
+
+ ### [Benchmark Results](https://github.com/mlemanczyk/Recyclable.Collections/blob/main/Recyclable.Collections.Benchmarks/Results/Benchmarks.md)
+
+# Architecture Decisions
+The architecture of the classes included in this project is driven primarily by performance & memory footprints. The following decisions were made to support it.
+
+## Code duplication
+There is high level of code duplication in each of the classes. When you look at them, you will see they are alike & some of the code could be extracted to extension methods. It has been done & has proven to perform worse. For this reason, properties & methods expected to be on the hot-path, duplicate much of the code to get the most out of it.
+
+## Common base - `ILongList`
+Having a common base class for all the classes looks very attractive. But it is also proved to perform worse, if you start making properties & methods virtual & there are subsequent calls to `base`. For this reason, each of the classes is the root class & there are hardly any virtual methods & properties. All classes are meant to be `final`, but I've not marked them as `sealed`. If you feel that you'd benefit from it, you're welcomed to inherit from them. The protected stuff is there for your use.
+
+If you desire to have a common base for calls, each of the classes implements `IList` & `ILongList` interfaces. `ILongList