You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
91 lines
2.8 KiB
91 lines
2.8 KiB
using System;
|
|
using System.Collections.Generic;
|
|
using System.Text;
|
|
|
|
namespace Infrastructure.Extensions
|
|
{
|
|
public static class Base62Extensions
|
|
{
|
|
private const string characterSet = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
|
|
|
|
public static string Base62Encode(this string value)
|
|
{
|
|
var arr = Encoding.UTF8.GetBytes(value);
|
|
return Base62Encode(arr);
|
|
}
|
|
|
|
public static string Base62Decode(this string value)
|
|
{
|
|
if (value is null)
|
|
{
|
|
throw new ArgumentNullException(nameof(value));
|
|
}
|
|
|
|
var arr = new byte[value.Length];
|
|
for (var i = 0; i < arr.Length; i++)
|
|
{
|
|
arr[i] = (byte)characterSet.IndexOf(value[i], StringComparison.CurrentCulture);
|
|
}
|
|
|
|
return Base62Decode(arr);
|
|
}
|
|
|
|
public static string Base62Encode(this byte[] value)
|
|
{
|
|
if (value is null)
|
|
{
|
|
throw new ArgumentNullException(nameof(value));
|
|
}
|
|
|
|
var converted = BaseConvert(value, 256, 62);
|
|
var builder = new StringBuilder();
|
|
for (var i = 0; i < converted.Length; i++)
|
|
{
|
|
builder.Append(characterSet[converted[i]]);
|
|
}
|
|
return builder.ToString();
|
|
}
|
|
|
|
public static string Base62Decode(this byte[] value)
|
|
{
|
|
if (value is null)
|
|
{
|
|
throw new ArgumentNullException(nameof(value));
|
|
}
|
|
|
|
var converted = BaseConvert(value, 62, 256);
|
|
|
|
return Encoding.UTF8.GetString(converted, 0, converted.Length);
|
|
}
|
|
|
|
private static byte[] BaseConvert(byte[] source, int sourceBase, int targetBase)
|
|
{
|
|
var result = new List<int>();
|
|
int count;
|
|
while ((count = source.Length) > 0)
|
|
{
|
|
var quotient = new List<byte>();
|
|
int remainder = 0;
|
|
for (var i = 0; i != count; i++)
|
|
{
|
|
int accumulator = source[i] + remainder * sourceBase;
|
|
byte digit = System.Convert.ToByte((accumulator - (accumulator % targetBase)) / targetBase);
|
|
remainder = accumulator % targetBase;
|
|
if (quotient.Count > 0 || digit != 0)
|
|
{
|
|
quotient.Add(digit);
|
|
}
|
|
}
|
|
|
|
result.Insert(0, remainder);
|
|
source = quotient.ToArray();
|
|
}
|
|
|
|
var output = new byte[result.Count];
|
|
for (int i = 0; i < result.Count; i++)
|
|
output[i] = (byte)result[i];
|
|
|
|
return output;
|
|
}
|
|
}
|
|
} |