C#dotnet core中同一属性的多个方法的自定义属性声明
正如我在另一个问题中所提到的,根据给出的答案,我能够使用以下代码调用/拒绝属性下的函数调用:C#dotnet core中同一属性的多个方法的自定义属性声明,c#,extension-methods,.net-core,custom-attributes,C#,Extension Methods,.net Core,Custom Attributes,正如我在另一个问题中所提到的,根据给出的答案,我能够使用以下代码调用/拒绝属性下的函数调用: using System; using System.Linq; // for using Where using System.Reflection; namespace attribute { public class Program { public static int Main(string[] args) { var customAttributes
using System;
using System.Linq; // for using Where
using System.Reflection;
namespace attribute
{
public class Program
{
public static int Main(string[] args)
{
var customAttributes = (MyCustomAttribute[])((typeof(Foo).GetTypeInfo())
.DeclaredMethods.Where(x => x.Name == "fn") // my question about this
.FirstOrDefault())
.GetCustomAttributes(typeof(MyCustomAttribute), true);
if (customAttributes.Length > 0)
{
var myAttribute = customAttributes[0];
string value = myAttribute.SomeProperty;
if (value == "bar")
Foo.fn();
else
Console.WriteLine("The attribute parameter is not as required");
}
return 0;
}
}
}
到目前为止,Attribute和Foo类都很简单,因为我正处于学习阶段:
[AttributeUsage(AttributeTargets.All)]
public class MyCustomAttribute : Attribute
{
public string SomeProperty { get; set; }
}
public class Foo
{
[MyCustom(SomeProperty = "bar")]
internal static void fn()
{
Console.WriteLine("a function in a class");
}
[MyCustom(SomeProperty = "bar")]
internal static void fn2()
{
Console.WriteLine("another function in the same class");
}
}
public class Foo2
{
[MyCustom(SomeProperty = "bar")]
internal static void fn2()
{
Console.WriteLine("another function in a nother class");
}
}
我的问题是关于.DeclaredMethods.Where(x=>x.Name==“fn”)
我是否需要为我添加的每个函数重复相同的操作,或者有一个简单的扩展可以为我执行此操作,我的目标很简单,我需要检查属性参数,如果它与我的输入匹配,我需要启动属性下的函数,如果不匹配,该函数将不会运行。谢谢
更新
将示例代码添加到ideone.com以便于检查
您可以准备所需的函数名的f.e.集合:
var targetFns = new HashSet<string>(new[] { "fn", "fn2","fn3" });
...
.DeclaredMethods.Where(x => targetFns.Contains(x.Name));
我会做一个像这样的通用方法
public static void CallMethod<T>(string methodName, string value)
{
var method = typeof(T).GetMethod(methodName, BindingFlags.DeclaredOnly | BindingFlags.Static | BindingFlags.NonPublic);
if (method == null)
{
Console.WriteLine("The method not found");
return;
}
foreach (var myAttribute in method.GetCustomAttributes<MyCustomAttribute>())
{
if (myAttribute.SomeProperty == value)
{
method.Invoke(null, null);
}
else
{
Console.WriteLine("The attribute parameter is not as required");
}
}
}
publicstaticvoidcallmethod(stringmethodname,stringvalue)
{
var method=typeof(T).GetMethod(methodName,BindingFlags.DeclaredOnly | BindingFlags.Static | BindingFlags.NonPublic);
if(方法==null)
{
Console.WriteLine(“未找到方法”);
返回;
}
foreach(方法.GetCustomAttributes()中的var myAttribute)
{
if(myAttribute.SomeProperty==值)
{
调用(null,null);
}
其他的
{
Console.WriteLine(“属性参数不符合要求”);
}
}
}
你可以调用它
CallMethod<Foo>("fn", "bar");
调用方法(“fn”、“bar”);
我假设您的方法是静态的。因此,它们不需要对象实例
static void ExecuteFunction(Type T,string functionName, string Value)
{
MethodInfo m = ((T.GetTypeInfo()).DeclaredMethods.Where(x => x.Name == functionName).FirstOrDefault());
//var customAttributes = (MyCustomAttribute[])((T.GetTypeInfo()).DeclaredMethods.Where(x => x.Name == functionName).FirstOrDefault()).GetCustomAttributes(typeof(MyCustomAttribute), true);
var customAttributes = (MyCustomAttribute[])(m.GetCustomAttributes(typeof(MyCustomAttribute), true));
if (customAttributes.Length > 0)
{
var myAttribute = customAttributes[0];
string value = myAttribute.SomeProperty;
// TODO: Do something with the value
Console.WriteLine(value);
if (value == Value)
{
m.Invoke(null, null);
}
else
Console.WriteLine("Unauthorized");
}
}
&执行为
ExecuteFunction(typeof(Foo), "fn", "bar");
编辑:
根据您的错误更新了解决方案:
您正在检查字符串。您应该根据字符串获取类&然后检查其中的方法
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using System.Reflection;
namespace ConsoleApp1Core
{
[AttributeUsage(AttributeTargets.All)]
public class MyCustomAttribute : Attribute
{
public string SomeProperty { get; set; }
}
public class Foo
{
[MyCustom(SomeProperty = "bar")]
internal static void fn()
{
Console.WriteLine("a function in a class");
}
[MyCustom(SomeProperty = "bar")]
internal static void fn2()
{
Console.WriteLine("another function in the same class");
}
}
public class Foo2
{
[MyCustom(SomeProperty = "bar")]
internal static void fn2()
{
Console.WriteLine("another function in a nother class");
}
}
public class Program
{
public static int Main(string[] args)
{
var targetClasses = new HashSet<string>(new[] { "ConsoleApp1Core.Foo", "ConsoleApp1Core.Foo2" });
var targetFns = new HashSet<string>(new[] { "fn", "fn2", "fn3" });
var j = 0;
foreach (var target in targetClasses)
{
Console.WriteLine("_class round {0}", j++);
var i = 0;
foreach (var fn in targetFns)
{
Console.WriteLine("fn round {0}", i++);
Type t = Type.GetType(target);
var method = (t.GetTypeInfo()) // (typeof(Foo).GetTypeInfo())
.DeclaredMethods.Where(x => x.Name == fn).FirstOrDefault();
if (method != null) //return 0;
{
var customAttributes = (MyCustomAttribute[])method
.GetCustomAttributes(typeof(MyCustomAttribute), true);
if (customAttributes.Length > 0)
{
var myAttribute = customAttributes[0];
string value = myAttribute.SomeProperty;
if (value == "bar")
method.Invoke(null, null);
// Foo.fn();;
else
Console.WriteLine("The attribute parameter is not as required");
}
}
else
{
Console.WriteLine("Method not found");
}
}
}
return 0;
}
}
}
使用系统;
使用System.Collections.Generic;
使用System.Linq;
使用System.Threading.Tasks;
运用系统反思;
名称空间控制台
{
[属性设置(AttributeTargets.All)]
公共类MyCustomAttribute:属性
{
公共字符串SomeProperty{get;set;}
}
公开课Foo
{
[MyCustom(SomeProperty=“bar”)]
内部静态空隙fn()
{
WriteLine(“类中的函数”);
}
[MyCustom(SomeProperty=“bar”)]
内部静态空隙fn2()
{
WriteLine(“同一类中的另一个函数”);
}
}
公开课2
{
[MyCustom(SomeProperty=“bar”)]
内部静态空隙fn2()
{
WriteLine(“另一个类中的另一个函数”);
}
}
公共课程
{
公共静态int Main(字符串[]args)
{
var targetClasses=newhashset(new[]{“ConsoleApp1Core.Foo”,“ConsoleApp1Core.Foo2”});
var targetFns=新哈希集(新[]{“fn”、“fn2”、“fn3”});
var j=0;
foreach(targetClasses中的var目标)
{
WriteLine(“{0}的类,j++”);
var i=0;
foreach(targetFns中的var fn)
{
WriteLine(“fn round{0}”,i++);
类型t=Type.GetType(目标);
var方法=(t.GetTypeInfo())/(typeof(Foo.GetTypeInfo())
.DeclaredMethods.Where(x=>x.Name==fn).FirstOrDefault();
if(method!=null)//返回0;
{
var customAttributes=(MyCustomAttribute[])方法
.GetCustomAttributes(typeof(MyCustomAttribute),true);
如果(customAttributes.Length>0)
{
var myAttribute=customAttributes[0];
字符串值=myAttribute.SomeProperty;
如果(值=“bar”)
调用(null,null);
//Foo.fn();;
其他的
Console.WriteLine(“属性参数不符合要求”);
}
}
其他的
{
Console.WriteLine(“未找到方法”);
}
}
}
返回0;
}
}
}
谢谢,bit如果(value==“bar”)Foo.fn(),我应该用什么来代替if(value==“bar”)代码>谢谢,如果我有不同的方法,比如Foo和Foo2,请查看我的问题编辑:)我尝试使用var targetClasses=new HashSet(new[]{“Foo”,“Foo2”})
和foreach(targetClasses中的var-target){var method=(typeof(target).GetTypeInfo())…}
但是在typeof(target)
@HasanAYousef而不是typeof use target.GetType()处出错,我使用了var method=(target.GetType().GetTypeInfo()).DeclaredMethods.Where(x=>targetFns.Contains(x.Name)).FirstOrDefault()
但是方法输出为null
可能是错误的,因为这里“var targetClasses=new HashSet(new[]{“Foo”,“Foo2”});
请还包括Foo类和属性用法。您的fn()似乎是一个静态方法,您只是试图调用该静态方法”fn“取决于属性上的某些属性?@JanneMatikainen我添加了请求的属性。如果使用GetCustomAttributes()@CSharpie yes,则不需要OfType。GetCustomAttributes将返回属性[],而不是直接强制转换类型。不,它返回IEnumerable,请参见yes,但在我的代码示例中提供了GetCustomAttributes(此MemberInfo,类型类型)将返回属性[]。我将修改我的答案以使用通用版本。奇怪的是,如果使用另一个签名,resharper不会重构以使用该扩展
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using System.Reflection;
namespace ConsoleApp1Core
{
[AttributeUsage(AttributeTargets.All)]
public class MyCustomAttribute : Attribute
{
public string SomeProperty { get; set; }
}
public class Foo
{
[MyCustom(SomeProperty = "bar")]
internal static void fn()
{
Console.WriteLine("a function in a class");
}
[MyCustom(SomeProperty = "bar")]
internal static void fn2()
{
Console.WriteLine("another function in the same class");
}
}
public class Foo2
{
[MyCustom(SomeProperty = "bar")]
internal static void fn2()
{
Console.WriteLine("another function in a nother class");
}
}
public class Program
{
public static int Main(string[] args)
{
var targetClasses = new HashSet<string>(new[] { "ConsoleApp1Core.Foo", "ConsoleApp1Core.Foo2" });
var targetFns = new HashSet<string>(new[] { "fn", "fn2", "fn3" });
var j = 0;
foreach (var target in targetClasses)
{
Console.WriteLine("_class round {0}", j++);
var i = 0;
foreach (var fn in targetFns)
{
Console.WriteLine("fn round {0}", i++);
Type t = Type.GetType(target);
var method = (t.GetTypeInfo()) // (typeof(Foo).GetTypeInfo())
.DeclaredMethods.Where(x => x.Name == fn).FirstOrDefault();
if (method != null) //return 0;
{
var customAttributes = (MyCustomAttribute[])method
.GetCustomAttributes(typeof(MyCustomAttribute), true);
if (customAttributes.Length > 0)
{
var myAttribute = customAttributes[0];
string value = myAttribute.SomeProperty;
if (value == "bar")
method.Invoke(null, null);
// Foo.fn();;
else
Console.WriteLine("The attribute parameter is not as required");
}
}
else
{
Console.WriteLine("Method not found");
}
}
}
return 0;
}
}
}