【发布时间】:2013-12-07 05:08:42
【问题描述】:
我正在编写一个扩展方法,通过删除大量样板来简化哈希的创建,但是我的问题是,每当我单步执行代码时,我都可以看到它总是选择@ 987654321@,不管我打给SHA256.Create(),SHA256Cng.Create(),SHA256Managed.Create()还是SHA256CryptoServiceProvider.Create()
当我选择不同的哈希算法(如 MD5)时,情况相同,但在 MD5 的情况下,它总是选择MD5CryptoServiceProvider,而不管我实际使用的类...
这是为什么呢?
这是我的代码:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Security.Cryptography;
using System.Text;
using System.Threading.Tasks;
namespace Utility.Methods
{
public enum HashType { MD5, SHA512, SHA256, SHA384, SHA1 }
public enum HashSubType {Normal, Cng, Managed, CryptoServiceProvider}
public static class TextHasher
{
public static string Hash(this string input, HashType hash, HashSubType subType = HashSubType.Normal)
{
Func<HashAlgorithm, string> hashFunction = alg => HashingHelper(input, alg);
switch (subType)
{
case HashSubType.Normal:
return hashFunction(NormalHashes(hash));
case HashSubType.Cng:
return hashFunction(CngHashes(hash));
case HashSubType.Managed:
return hashFunction(ManagedHashes(hash));
case HashSubType.CryptoServiceProvider:
return hashFunction(CSPHashes(hash));
default: return "error"; // unreachable
}
}
private static string HashingHelper(string text, HashAlgorithm algorithm)
{
Func<string, byte[]> getHash = input => algorithm.ComputeHash(Encoding.UTF8.GetBytes(input));
var sb = new StringBuilder();
Array.ForEach(getHash(text), b => sb.Append(b.ToString("X")));
return sb.ToString();
}
private static HashAlgorithm NormalHashes(HashType hash)
{
switch (hash)
{
case HashType.MD5:
return MD5.Create();
case HashType.SHA1:
return SHA1.Create();
case HashType.SHA256:
return SHA256.Create();
case HashType.SHA384:
return SHA384.Create();
case HashType.SHA512:
return SHA512.Create();
default: return null; // unreachable
}
}
private static HashAlgorithm CngHashes(HashType hash)
{
switch (hash)
{
case HashType.MD5:
return MD5Cng.Create();
case HashType.SHA1:
return SHA1Cng.Create();
case HashType.SHA256:
return SHA256Cng.Create();
case HashType.SHA384:
return SHA384Cng.Create();
case HashType.SHA512:
return SHA512Cng.Create();
default: return null; // unreachable
}
}
private static HashAlgorithm ManagedHashes(HashType hash)
{
switch (hash)
{
case HashType.SHA1:
return SHA1Managed.Create();
case HashType.SHA256:
return SHA256Managed.Create();
case HashType.SHA384:
return SHA384Managed.Create();
case HashType.SHA512:
return SHA512Managed.Create();
default: return null; // unreachable
}
}
private static HashAlgorithm CSPHashes(HashType hash)
{
switch (hash)
{
case HashType.MD5:
return MD5CryptoServiceProvider.Create();
case HashType.SHA1:
return SHA1CryptoServiceProvider.Create();
case HashType.SHA256:
return SHA256CryptoServiceProvider.Create();
case HashType.SHA384:
return SHA384CryptoServiceProvider.Create();
case HashType.SHA512:
return SHA512CryptoServiceProvider.Create();
default: return null; // unreachable
}
}
}
}
那么,有什么帮助吗?
【问题讨论】:
-
这并不特别令人惊讶(但我认为它应该会生成警告),因为
Create是在SHA256类上静态定义的,并且其他类继承自该类,所以你'在每种情况下都调用相同的方法。非抽象类有公共构造函数。 -
那么如果 create 方法没有改变它正在做的事情,那么拥有其他版本的类有什么意义呢?
-
因为这些类的实例做不同的事情。它们只是与您的用例无关。
-
1) 你可以直接construct 其他版本的类,如果你想获得的话,2) 你可以使用
Create的重载,它接受一个字符串来选择一个非默认值,以及 3) 如果您使用此重载,要构造的类是在机器级别配置的,而不是硬编码的。 -
如果文档没有指定使用哪些字符串是合法的,那将不是很有帮助...我基本上可以这样做
SHA256.Create("Dog");
标签: c# hash md5 checksum sha256