Swap bit between MSB and LSB
Original code is from https://ja.stackoverflow.com/a/9239/882 . CC BY-SA 3.0
## 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/ | |
[Ww][Ii][Nn]32/ | |
[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/ | |
# ASP.NET Scaffolding | |
ScaffoldingReadMe.txt | |
# 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 | |
*.tlog | |
*.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 | |
# Coverlet is a free, cross platform Code Coverage Tool | |
coverage*.json | |
coverage*.xml | |
coverage*.info | |
# 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 | |
# Nuget personal access tokens and Credentials | |
nuget.config | |
# 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/ | |
# Fody - auto-generated XML schema | |
FodyWeavers.xsd | |
# VS Code files for those working on multiple tools | |
.vscode/* | |
!.vscode/settings.json | |
!.vscode/tasks.json | |
!.vscode/launch.json | |
!.vscode/extensions.json | |
*.code-workspace | |
# Local History for Visual Studio Code | |
.history/ | |
# Windows Installer files from build outputs | |
*.cab | |
*.msi | |
*.msix | |
*.msm | |
*.msp | |
# JetBrains Rider | |
.idea/ | |
*.sln.iml |
Swap bit between MSB and LSB
Original code is from https://ja.stackoverflow.com/a/9239/882 . CC BY-SA 3.0
using System; | |
namespace BitReverse | |
{ | |
/// <summary> | |
/// Swap MSB and LSB | |
/// </summary> | |
public static class BitReverse | |
{ | |
/// <summary> | |
/// Swap MSB and LSB | |
/// </summary> | |
/// <param name="input">input number</param> | |
/// <returns>Swapped input number</returns> | |
public static ulong UInt64(ulong input) | |
{ | |
return ReverseBit(input, 64); | |
} | |
/// <summary> | |
/// Swap MSB and LSB | |
/// </summary> | |
/// <param name="input">input number</param> | |
/// <returns>Swapped input number</returns> | |
public static uint UInt32(uint input) | |
{ | |
return (uint)ReverseBit(input, 32); | |
} | |
/// <summary> | |
/// Swap MSB and LSB | |
/// </summary> | |
/// <param name="input">input number</param> | |
/// <returns>Swapped input number</returns> | |
public static ushort UInt16(ushort input) | |
{ | |
return (ushort)ReverseBit(input, 16); | |
} | |
/// <summary> | |
/// Swap MSB and LSB | |
/// </summary> | |
/// <param name="input">input number</param> | |
/// <returns>Swapped input number</returns> | |
public static byte UInt8(byte input) | |
{ | |
return (byte)ReverseBit(input, 8); | |
} | |
/// <summary> | |
/// Swap MSB and LSB | |
/// </summary> | |
/// <param name="input">input number</param> | |
/// <param name="bit">size of bits</param> | |
/// <returns>Swapped input number</returns> | |
/// <remarks> | |
/// Original code is from https://ja.stackoverflow.com/a/9239/882 | |
/// </remarks> | |
private static ulong ReverseBit(ulong input, int bit) | |
{ | |
ulong swap = input; | |
switch (bit) | |
{ | |
case 64: | |
swap = ((swap & 0x00000000ffffffff) << 32) | ((swap >> 32) & 0x00000000ffffffff); | |
goto case 32; | |
case 32: | |
swap = ((swap & 0x0000ffff0000ffff) << 16) | ((swap >> 16) & 0x0000ffff0000ffff); | |
goto case 16; | |
case 16: | |
swap = ((swap & 0x00ff00ff00ff00ff) << 8) | ((swap >> 8) & 0x00ff00ff00ff00ff); | |
goto case 8; | |
case 8: | |
swap = ((swap & 0x0f0f0f0f0f0f0f0f) << 4) | ((swap >> 4) & 0x0f0f0f0f0f0f0f0f); | |
goto case 4; | |
case 4: | |
swap = ((swap & 0x3333333333333333) << 2) | ((swap >> 2) & 0x3333333333333333); | |
goto case 2; | |
case 2: | |
swap = ((swap & 0x5555555555555555) << 1) | ((swap >> 1) & 0x5555555555555555); | |
break; | |
default: | |
throw new ArgumentException("bit is out of range: 2/4/8/16/32/64", nameof(bit)); | |
} | |
return swap; | |
} | |
} | |
} |
<Project Sdk="Microsoft.NET.Sdk"> | |
<PropertyGroup> | |
<TargetFramework>netcoreapp3.1</TargetFramework> | |
<IsPackable>false</IsPackable> | |
<EnableNETAnalyzers>true</EnableNETAnalyzers> | |
</PropertyGroup> | |
<ItemGroup> | |
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="16.5.0" /> | |
<PackageReference Include="MSTest.TestAdapter" Version="2.1.0" /> | |
<PackageReference Include="MSTest.TestFramework" Version="2.1.0" /> | |
<PackageReference Include="coverlet.collector" Version="1.2.0" /> | |
</ItemGroup> | |
</Project> |
| |
Microsoft Visual Studio Solution File, Format Version 12.00 | |
# Visual Studio Version 16 | |
VisualStudioVersion = 16.0.31004.235 | |
MinimumVisualStudioVersion = 10.0.40219.1 | |
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "BitReverse", "BitReverse.csproj", "{EA5230BD-3AA0-4876-88B4-31F0607EA287}" | |
EndProject | |
Global | |
GlobalSection(SolutionConfigurationPlatforms) = preSolution | |
Debug|Any CPU = Debug|Any CPU | |
Release|Any CPU = Release|Any CPU | |
EndGlobalSection | |
GlobalSection(ProjectConfigurationPlatforms) = postSolution | |
{EA5230BD-3AA0-4876-88B4-31F0607EA287}.Debug|Any CPU.ActiveCfg = Debug|Any CPU | |
{EA5230BD-3AA0-4876-88B4-31F0607EA287}.Debug|Any CPU.Build.0 = Debug|Any CPU | |
{EA5230BD-3AA0-4876-88B4-31F0607EA287}.Release|Any CPU.ActiveCfg = Release|Any CPU | |
{EA5230BD-3AA0-4876-88B4-31F0607EA287}.Release|Any CPU.Build.0 = Release|Any CPU | |
EndGlobalSection | |
GlobalSection(SolutionProperties) = preSolution | |
HideSolutionNode = FALSE | |
EndGlobalSection | |
GlobalSection(ExtensibilityGlobals) = postSolution | |
SolutionGuid = {2DB039F7-39F9-437E-A189-BBF37BB48600} | |
EndGlobalSection | |
EndGlobal |
using System; | |
using System.Security.Cryptography.X509Certificates; | |
namespace BitReverse | |
{ | |
/// <summary> | |
/// Swap MSB and LSB | |
/// </summary> | |
public static class BitReverseLoop | |
{ | |
/// <summary> | |
/// Swap MSB and LSB | |
/// </summary> | |
/// <param name="input">input number</param> | |
/// <returns>Swapped input number</returns> | |
public static ulong UInt64(ulong input) | |
{ | |
return ReverseBit(input, 64); | |
} | |
/// <summary> | |
/// Swap MSB and LSB | |
/// </summary> | |
/// <param name="input">input number</param> | |
/// <returns>Swapped input number</returns> | |
public static uint UInt32(uint input) | |
{ | |
return (uint)ReverseBit(input, 32); | |
} | |
/// <summary> | |
/// Swap MSB and LSB | |
/// </summary> | |
/// <param name="input">input number</param> | |
/// <returns>Swapped input number</returns> | |
public static ushort UInt16(ushort input) | |
{ | |
return (ushort)ReverseBit(input, 16); | |
} | |
/// <summary> | |
/// Swap MSB and LSB | |
/// </summary> | |
/// <param name="input">input number</param> | |
/// <returns>Swapped input number</returns> | |
public static byte UInt8(byte input) | |
{ | |
return (byte)ReverseBit(input, 8); | |
} | |
/// <summary> | |
/// Swap MSB and LSB | |
/// </summary> | |
/// <param name="input">input number</param> | |
/// <param name="bit">size of bits</param> | |
/// <returns>Swapped input number</returns> | |
/// <remarks> | |
/// Original code is from https://ja.stackoverflow.com/a/7500/882 | |
/// </remarks> | |
private static ulong ReverseBit(ulong input, int bit) | |
{ | |
ulong swap = 0; | |
while(bit-- > 0) | |
{ | |
swap <<= 1; | |
swap |= (input & 1u); | |
input >>= 1; | |
} | |
return swap; | |
} | |
} | |
} |
#define BITREVERSE | |
#define BITREVERSELOOP | |
using Microsoft.VisualStudio.TestTools.UnitTesting; | |
using System; | |
using System.Diagnostics; | |
using System.Linq; | |
namespace BitReverse | |
{ | |
[TestClass] | |
public class BitReverseTest | |
{ | |
[TestMethod] | |
public void TestUnit64() | |
{ | |
ulong input = 0x0000000000000001u; | |
ulong result; | |
#if BITREVERSE | |
result = BitReverse.UInt64(input); | |
Assert.AreEqual(0x8000000000000000uL, result); | |
#endif | |
#if BITREVERSELOOP | |
result = BitReverseLoop.UInt64(input); | |
Assert.AreEqual(0x8000000000000000uL, result); | |
#endif | |
} | |
[TestMethod] | |
public void TestUnit32() | |
{ | |
uint input = 0x00000001u; | |
uint result; | |
#if BITREVERSE | |
result = BitReverse.UInt32(input); | |
Assert.AreEqual(0x80000000u, result); | |
#endif | |
#if BITREVERSELOOP | |
result = BitReverseLoop.UInt32(input); | |
Assert.AreEqual(0x80000000u, result); | |
#endif | |
} | |
[TestMethod] | |
public void TestUnit16() | |
{ | |
ushort input = (ushort)0x0001u; | |
ushort result; | |
#if BITREVERSE | |
result = BitReverse.UInt16(input); | |
Assert.AreEqual(0x8000u, result); | |
#endif | |
#if BITREVERSELOOP | |
result = BitReverseLoop.UInt16(input); | |
Assert.AreEqual(0x8000u, result); | |
#endif | |
} | |
[TestMethod] | |
public void TestUnit8() | |
{ | |
byte input = (byte)0x01u; | |
byte result; | |
#if BITREVERSE | |
result = BitReverse.UInt8(input); | |
Assert.AreEqual(0x80u, result); | |
#endif | |
#if BITREVERSELOOP | |
#endif | |
} | |
[TestMethod] | |
public void TestSpeed64() | |
{ | |
var sw = new Stopwatch(); | |
var rand = new Random(0x1234); | |
var testData = Enumerable.Range(1, 100000).Select((w, i) => new | |
{ | |
#pragma warning disable CS0675 | |
Value = (ulong)((((ulong)rand.Next()) << 32) | (ulong)rand.Next()), | |
#pragma warning restore CS0675 | |
Index = i, | |
}).ToArray(); | |
#if BITREVERSE | |
var result = new ulong[testData.Length]; | |
sw.Start(); | |
foreach (var item in testData) | |
{ | |
result[item.Index] = BitReverse.UInt64(item.Value); | |
} | |
var lap = sw.ElapsedMilliseconds; | |
sw.Stop(); | |
Console.WriteLine("Test ran {1} items in {0}ms", lap, testData.Length); | |
sw.Reset(); | |
#endif | |
#if BITREVERSELOOP | |
var resultLoop = new ulong[testData.Length]; | |
sw.Start(); | |
foreach (var item in testData) | |
{ | |
resultLoop[item.Index] = BitReverseLoop.UInt64(item.Value); | |
} | |
var lapLoop = sw.ElapsedMilliseconds; | |
sw.Stop(); | |
Console.WriteLine("Test ran loop {1} items in {0}ms", lapLoop, testData.Length); | |
#endif | |
#if BITREVERSE | |
foreach (var item in testData) | |
{ | |
Console.WriteLine("{0,0:X8} ¨ {1,0:X8}", item.Value, result[item.Index]); | |
} | |
#endif | |
sw.Reset(); | |
} | |
} | |
} |