擴展方法
擴展方法使你能夠向現有類型“添加”方法,而無需創建新的派生類型、重新編譯或以其他方式修改原始類型。 擴展方法是一種靜態方法,但可以像擴展類型上的實例方法一樣進行調用。
實現一個靜態擴展方法
現在有個需求,需要對密碼進行 SHA512 加密,才可以存放進入數據庫中,但是每次通過其他方法調用比較麻煩,有沒有一種可以直接連續點出來的方法呢?
連續點的方法一般都是靜態方法,而且官方提供了靜態方法擴展的可操作性,所以我們可以實現一個自定義的擴展方法。
而加密一般都為字符串,所以只需要在字符串上進行擴展即可。
擴展方法被定義為靜態方法,但它們是通過實例方法語法進行調用的。 它們的第一個參數指定方法操作的類型。
參數前面是此修飾符。 僅當你使用 using 指令將命名空間顯式導入到源代碼中之后,擴展方法才位於范圍中。
將類型放入到靜態方法中
public static class StringExtension {
public static string ConvertSHA512(this string currentStr){
// 現在在函數參數中的 `currentStr` 就是這個函數的字符串
}
}
"name".SHA512() 時,上面的 currentStr 就是 "name"這個字符串。
而所謂的靜態類型並沒有什么用,只是方便你用來區分擴展方法是那個范圍的。
當然你在使用擴展方法時,需要引用當前靜擴展函數所在的命名空間才行。
現在你在這個函數中已經拿到了當前執行函數的字符串,那么就可以對這個字符串進行一些操作了。
實現 SHA512 加密
public static class StringExtension {
public static string ConvertSHA512(this string currentStr)
{
var bytes = Encoding.UTF8.GetBytes(currentStr);
using (var hash = SHA512.Create())
{
var hashedInputBytes = hash.ComputeHash(bytes);
// Convert to text
// StringBuilder Capacity is 128, because 512 bits / 8 bits in byte * 2 symbols for byte
var hashedInputStringBuilder = new StringBuilder(128);
foreach (var b in hashedInputBytes)
hashedInputStringBuilder.Append(b.ToString("X2"));
return hashedInputStringBuilder.ToString();
}
}
}
在靜態擴展方法中對傳遞進來的字符串進行加密,然后返回回去。當然你可以返回任何類型的數據,但是一旦返回的類型變化了,那么你在連點調用加密函數后,只能繼續點返回的類型的方法,而不能在繼續使用字符串的方法了。
一些擴展方法的例子
字符串相關的擴展方法
namespace BlogSite.CommonLib
{
public static class StringExtension
{
/// <summary>
/// 將字符串進行SHA512加密
/// </summary>
/// <param name="s"></param>
/// <returns></returns>
public static string ConvertSHA512(this string s)
{
var bytes = Encoding.UTF8.GetBytes(s);
using (var hash = SHA512.Create())
{
var hashedInputBytes = hash.ComputeHash(bytes);
// Convert to text
// StringBuilder Capacity is 128, because 512 bits / 8 bits in byte * 2 symbols for byte
var hashedInputStringBuilder = new StringBuilder(128);
foreach (var b in hashedInputBytes)
hashedInputStringBuilder.Append(b.ToString("X2"));
return hashedInputStringBuilder.ToString();
}
}
public static bool IsNullOrWhiteSpace(this string s)
{
return string.IsNullOrWhiteSpace(s);
}
public static bool IsNullOrEmpty(this string s)
{
return string.IsNullOrEmpty(s);
}
/// <summary>
/// 首字母大寫
/// </summary>
public static string ToUpperFirstLetter(this string value)
{
if (value.IsNullOrWhiteSpace())
{
return string.Empty;
}
char[] letters = value.ToCharArray();
letters[0] = char.ToUpper(letters[0]);
return new string(letters);
}
/// <summary>
/// 首字母小寫
/// </summary>
public static string ToLowerFirstLetter(this string value)
{
if (value.IsNullOrWhiteSpace())
{
return string.Empty;
}
char[] letters = value.ToCharArray();
letters[0] = char.ToLower(letters[0]);
return new string(letters);
}
/// <summary>
/// 字符串轉大寫
/// </summary>
public static string ToLower(this string value)
{
if (value.IsNullOrWhiteSpace())
{
return string.Empty;
}
char[] letters = value.ToCharArray();
for (int i = 0; i < letters.Length; i++)
{
letters[i] = char.ToLower(letters[i]);
}
return new string(letters);
}
}
}
Enum 枚舉擴展方法
namespace BlogSite.CommonLib
{
/// <summary>
/// Enum 靜態擴展方法
/// </summary>
public static class EnumExtension
{
/// <summary>
/// 獲取枚舉值上的Description特性的說明
/// </summary>
/// <returns>特性的說明</returns>
public static string GetDescription(this Enum en)
{
var type = en.GetType();
FieldInfo field = type.GetField(Enum.GetName(type, en));
if (!(Attribute.GetCustomAttribute(field, typeof(DescriptionAttribute)) is DescriptionAttribute descAttr))
{
return string.Empty;
}
return descAttr.Description;
}
}
}
結束
當然擴展方法在實際中很是常用的,擴展方法比較好寫,但是比較難的在於函數內部的一些實現,所以這些需要多寫寫,多練練。
