了解常用的特性

浅析 AssemblyInfo.cs – 领悟常用的风味 Attribute

【博主】反骨仔    【原文】

 

 性格(Attributes)是1种斩新的注脚性新闻。我们不但能够透过特征来定义设计规模的新闻(比方help
file, U福睿斯L for
documentation)以及运营时(run-time)音信(举例使XML与class相联系),而且我们还足以行使特色创设自描述(self-
describing)组件。在那篇教程中,大家将会看到什么样树立和加多天性到各类程序实体以及咋样在运营时蒙受中赢得天性消息。

民用定义:不凌犯对象的情形下,加多对象附注消息。

图片 1

  

   定义

官方概念:将预订义的系统新闻或用户定义的自定义务消防队息与目的成分相关联。目的成分得以是程序集、类、构造函数、委托、枚举、事件、字段、接口、方法、可移植可实践文件模
  块、参数、属性 (Property)、再次回到值、结构或其它属性
(Attribute)。提供的音讯也称为元数据,元数据可由应用程序在运营时实行反省以调节造进程序管理数据的章程,也得以由外部工具在运作前检查以调整应用程序管理或保养自个儿的艺术。

  在此之前,我们通过《C# 知识回想 – 特性Attribute》已经领会什么创建和动用本性Attribute,此番,让大家联合来看看每趟使用 VS
创设项目时所自带的文件 AssemblyInfo.cs。

 

   正如MSDN中所描述的那样—–  

.Net 框架提供了二种预约义个性:

目录

  • 全局性格
  • 已不合时宜的特色:Obsolete
  • 标准天性:Conditional
  • 调用方新闻天性

 

   “天性是被钦赐给某一声称的1则附加的证明性音信。”  

  • AttributeUsage
  • Conditional
  • Obsolete

AssemblyInfo.cs

图片 2

私下挑选二个 AssemblyInfo.cs 文件,张开图中的代码,看箭头↓

using System.Reflection;
using System.Runtime.InteropServices;

// 有关程序集的常规信息通过下列特性集
// 控制。更改这些特性值可修改
// 与程序集关联的信息。
[assembly: AssemblyTitle("MusicStore")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("Microsoft")]
[assembly: AssemblyProduct("MusicStore")]
[assembly: AssemblyCopyright("Copyright © Microsoft 2016")]
[assembly: AssemblyTrademark("")]
[assembly: AssemblyCulture("")]

// 将 ComVisible 设置为 false 会使此程序集中的类型
// 对 COM 组件不可见。如果需要
// 从 COM 访问此程序集中的某个类型,请针对该类型将 ComVisible 特性设置为 true。
[assembly: ComVisible(false)]

// 如果此项目向 COM 公开,则下列 GUID 用于 typelib 的 ID
[assembly: Guid("a9ef3281-9049-4a52-a2f1-2061d442200e")]

// 程序集的版本信息由下列四个值组成:
//
//      主版本
//      次版本
//      内部版本号
//      修订版本
//
// 可以指定所有值,也可以使用“修订号”和“内部版本号”的默认值,
// 方法是按如下所示使用 "*":
[assembly: AssemblyVersion("1.0.0.0")]
[assembly: AssemblyFileVersion("1.0.0.0")]

 

  使用预定义(Pre-defined)天性  

演示: 读取枚举值上加的 天性消息

一、全局脾气

  大大多特点适用于特定的言语因素(如类或艺术),不过,有种性格它们适用于整个程序集或模块,称为全局性子。如:AssemblyVersionAttribute 天性可用于向程序聚集停放版本音讯。

图片 3

 

  全局特性在源代码中冒出在其余拔尖 using 指令以及其它项目、模块或命名空间申明在此之前。全局天性可兆示在多少个源文件,不过,在单一编写翻译传递必须编写翻译文件。在
C# 项目中,它们在 AssemblyInfo.cs 文件中。

  程序集天性是提供有关程序集的新闻的值。它们分成以下连串:

    1先后集标记脾气

了解常用的特性。    2消息性个性

    叁程序集清单特性

    四强名称脾性

  

  一.顺序集标志天性

  四个特色 (使用强名称,假使适用)
显明程序集的标志:名称、版本和区域性。当在代码中援引时,那些特点构成程序集的完好名称要求。使用天性,能够将先后集的本子、区域性和名称值,由编写翻译器,在 “程序集新闻”对话框 的
Visual Studio IDE
设置,在创造程序集后,依据包括程序集清单的文本。AssemblyFlagsAttribute 天性内定程序集的七个别本是不是足以共存。

图片 4

 

图片 5

图 – “程序集音讯”对话框

图片 6

图 – “程序集音讯”对话框中的名词和 AssemblyInfo.cs 文件的对应关系

 

  二.新闻性性格

  您能够行使音讯性性情为顺序集提供任何的店肆或产品新闻。

图片 7

 

  三.程序集清单性情

  能够选用程序集清单性子提供程序集清单中的音信。当中包蕴标题、表明、默许别称和安顿。

图片 8

 

  四.强名号天性(不深切)

  一般存在 Visual Studio
的最初版本,若要使用强名称的主次集实践以下顺序集等级本性:

    ①AssemblyKeyFileAttribute

    ②AssemblyKeyNameAttribute

    ③AssemblyDelaySignAttribute

  纵然今后仍补助,但是,给程序集具名的主推办法是选择“具名页”。(这里不深刻精晓)

 

  在C#中,有八个小的预订义性格集结。在就学怎么着创设大家温馨的定制性情(custom
attributes)在此以前,大家先来看看在大家的代码中怎么着行使预订义天性。  

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace MyAttribute
{
    [Obsolete("这是一个过期特性")]
    public enum EnumState
    {       
        [Remark("我是打开")]
        //[Remark("")]
        Open =1,
        [Remark("我是关闭")]
        Close=2
    }
}

贰、已不合时宜的特色:Obsolete

   Obsolete 个性提示有个别程序实体标志为提议不再利用的3个。
每一趟使用对实业标志为过时遵照随后将生成警告或错误。

 1     /// <summary>
 2     /// 旧类
 3     /// </summary>
 4     [Obsolete("请使用 " + nameof(NewClass))]
 5     class OldClass
 6     {
 7         public void Method() { }
 8     }
 9 
10     /// <summary>
11     /// 新类
12     /// </summary>
13     class NewClass
14     {
15         [Obsolete("请使用 " + nameof(NewMethod), true)]
16         public void OldMethod() { }
17 
18         public void NewMethod() { }
19     }

 1     class Program
 2     {
 3         static void Main(string[] args)
 4         {
 5             var oldClass = new OldClass();  //警告
 6 
 7             var newClass = new NewClass();
 8             newClass.OldMethod();  //报错
 9         }
10     }

图片 9

  在此示例中应用 Obsolete 特性类 OldClass 和方法
NewClass.OldMethod。此构造函数的率先个参数为警告或错误的新闻,由于本性构造函数的第三个参数被选取于
NewClass.OldMethod 设置为 true,此措施将促成编写翻译器错误,而选取 OldClass 只将生成警告的类。

 

  using System;

 

三、条件性格:Conditional

Conditional 性格执市场价格势依赖于预管理标记符。Conditional 属性是 ConditionalAttribute 的外号,可选用于方法或属性类。

  在此示例中,Conditional 应用于方法以启用或剥夺程序一定会诊音信示:

 1     class Debug
 2     {
 3         [Conditional("DEBUG")]
 4         public static void Output(string msg)
 5         {
 6             Console.WriteLine(msg);
 7         }
 8     }
 9 
10     class Program
11     {
12         static void Main(string[] args)
13         {
14             Debug.Output("This is Debug!");
15             Console.WriteLine("Done!");
16 
17             Console.Read();
18         }
19     }

  Conditional 天性温日用于在 DEBUG 标志符启用追踪,并记下的职能的调理版本,但不在公布版本中。

图片 10

  

  将事先的代码轻便改变下,使用 #if…#endif 包扎,结果和上海教室是同等的。

    class Debug
    {
        public static void Output(string msg)
        {
            Console.WriteLine(msg);
        }
    }

    class Program
    {
        static void Main(string[] args)
        {
            #if DEBUG
            Debug.Output("This is Debug!");
            #endif

            Console.WriteLine("Done!");

            Console.Read();
        }
    }

  使用 Conditional 越发卫生,当然也能够将平日不太到用到也许轻巧失误的法子在 #if…#endif 内部块标明。

图片 11

 

  public class AnyClass

using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Reflection;
using System.Text;
using System.Threading.Tasks;

namespace MyAttribute
{
  //1.特性的适用范围  2.特性是否允许用多次 3.特性是否被派生类继承
    [AttributeUsage(AttributeTargets.All,AllowMultiple =true, Inherited =true)]
  //被调用时执行条件编译,取决于指定的值(如“DEBUG”,"RELEASE"...)
    [Conditional("DEBUG")]
    public class RemarkAttribute:Attribute
    {
        public string remark;

        public string Remark
        {
            get { return remark; }
        }

        public RemarkAttribute(string remark)
        {
            this.remark = remark;
        }
    }

    public static class RemarkExtend
    {
        public static string RemarkDescription(this EnumState state)
        {
            Type type = typeof(EnumState);
            FieldInfo info= type.GetField(state.ToString());
            object[] remarkCustomAttribute= info.GetCustomAttributes(typeof(RemarkAttribute),false);     
            if(remarkCustomAttribute != null && remarkCustomAttribute.Length>0)
            {
                RemarkAttribute remarkattribute = remarkCustomAttribute[0] as RemarkAttribute;
                return remarkattribute.Remark;
            }
            else
            {
                return state.ToString();
            }
        }
    }
}

肆、调用方消息性情

  使用调用方音信属性,可以获取有关调用方的音讯传递给艺术。能够收获源代码、行号在源代码和调用方的分子名称的公文路线。

  若要获取成员调用方音信,请使用适用于可选参数的本性。每种可选参数钦赐默许值。

图片 12

 

 1     internal class Program
 2     {
 3         private static void Main(string[] args)
 4         {
 5             CallerMethod();
 6             Console.Read();
 7         }
 8 
 9         public static void CallerMethod()
10         {
11             TraceMessage("我是调用者");
12         }
13 
14         public static void TraceMessage(string msg,
15             [CallerMemberName] string name = "",
16             [CallerFilePath] string filePath = "",
17             [CallerLineNumber] int lineNumer = 0)
18         {
19             Trace.WriteLine($"{nameof(msg)}: {msg}");
20             Trace.WriteLine($"{nameof(name)}: {name}");
21             Trace.WriteLine($"{nameof(filePath)}: {filePath}");
22             Trace.WriteLine($"{nameof(lineNumer)}: {lineNumer}");
23         }
24     }

图片 13

  每一趟调用 CallerMethod 方法时,调用方消息将替换为可选参数的变量。

 

  1.备注

  你必须为各类可选参数钦点显式暗中认可值。不可能将调用方新闻天性应用于未钦赐为可选的参数。

  调用方新闻本性不会使参数成为可选参数。相反,它们会在不经意此参数时影响传播的私下认可值。

  在编写翻译时,调用方音讯值将用作文本传入中间语言
(IL)。与丰裕的 StackTrace 性子的结果差别,这一个结果不受模糊管理的震慑。

  你可显式提供可选参数来决定调用方新闻或隐藏调用方音信。

 

  {

 

传送门

  《C# 知识回看 – 天性Attribute》

  《C# 知识回顾 –
种类化》

  《C# 知识回想 – 表明式树 Expression
Trees》

 

 


【参考】微软官方文书档案

 

   [Obsolete(“Don’t use Old method, use New method”, true)]

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace MyAttribute
{
    class Program
    {
        static void Main(string[] args)
        {
            EnumState state = EnumState.Open;
            Console.WriteLine(state.RemarkDescription());
            Console.Read();
        }
    }
}

   static void Old( ) { }  

至此,关于性格的读书就到此结束了,多谢你的开卷。

   static void New( ) { }  

特征还有许多高档的用法,博主只是小规模试制牛刀,希望本文能够帮到你,当然若有不到家地点,接待斧正。

   public static void Main( )

参考MSDN:

   {

 

   Old( );

   }

  }

  大家先来看一下方面那个事例,在那一个事例中大家选用了Obsolete个性,它标记了三个不应有再被使用的次序实体。第一个参数是一个字符串,它表达了干吗该实体是不合时宜的以及相应用哪些实体来顶替它。实际上,你能够在此处写任何公文。第三个参数告诉编写翻译器应该把利用这一个过时的主次实体当作
壹种错误。它的默许值是false,也正是说编写翻译器对此会发出3个警示。  

  当大家尝试编写翻译上边那段程序的时候,大家将会获得3个错误:  

  AnyClass.Old()’ is obsolete: ‘Don’t use Old method, use New method’  
 

  开荒定制个性(custom attributes) 

  以后让我们来看望哪些开垦我们协和的特征。 

  首先我们要从System.Attribute派生出我们本人的表征类(2个从System.Attribute抽象类承继而来的类,不管是直接或然间接接轨,都会形成三个特点类。特性类的扬言定义了一种可以被停放在宣称之上新的特点)。
 

  using System;

  public class HelpAttribute : Attribute

  {

  }

  不管你是还是不是相信,大家早就创制了四个定制性格,今后大家能够用它来装饰现存的类就像是上边我们运用Obsolete
attribute同样。  

  [Help()]

  public class AnyClass

  {

  }

  注意:对贰个特色类名使用Attribute后缀是一个惯例。然则,当大家把特色增添到一个程序实体,是不是包涵Attribute后缀是咱们的轻便。编写翻译器会首先在System.Attribute的派生类中找找被增多的风味类。要是未有找到,那么编写翻译器会增进Attribute后缀继续查
找。  

  到最近停止,那些特点还尚未起到哪些作用。下边大家来加多些东西给它使它更有用些。
 

  using System;

  public class HelpAttribute : Attribute

  {

   public HelpAttribute(String Descrition_in)

   {

   this.description = Description_in;

   }

   protected String description;

   public String Description

   {

   get

   {

   return this.description;  

   }

   }

  }

  [Help(“this is a do-nothing class”)]

  public class AnyClass

发表评论

电子邮件地址不会被公开。 必填项已用*标注

网站地图xml地图