GVKun编程网logo

c# – 使用参数在expression.call中调用静态方法(c#怎么调用静态方法)

15

在这里,我们将给大家分享关于c#–使用参数在expression.call中调用静态方法的知识,让您更了解c#怎么调用静态方法的本质,同时也会涉及到如何更有效地ABAPmeshexpression,J

在这里,我们将给大家分享关于c# – 使用参数在expression.call中调用静态方法的知识,让您更了解c#怎么调用静态方法的本质,同时也会涉及到如何更有效地ABAP mesh expression, JavaScript and Scala expression、ArcGis 字段计算器表达式(Field calculator expression).cal文件与标注表达式(label expression).lxp的实质及其编码方式、解析方法、asp.net-mvc – HTMLHelper,从属性中生成“Expression> expression”类型的参数、c – 有没有办法在使用clang的VisitCallExpr方法中获取CallExpr *的调用者?的内容。

本文目录一览:

c# – 使用参数在expression.call中调用静态方法(c#怎么调用静态方法)

c# – 使用参数在expression.call中调用静态方法(c#怎么调用静态方法)

我已经扩展了Contains方法的字符串类.我试图在Expression.Call中调用它,但如何正确传递参数?

代码:String包含方法:

public static class StringExts
{
    public static bool NewContains(this string source,string Valtocheck,StringComparison StrComp)
    {
        return source.IndexOf(Valtocheck,StrComp) >= 0;
    }
}

在表达式中调用为:

public class Person { public string Name {get; set;} }

public class Persons { 
    public List<Person> lstPersons {get; set;} 
    public Persons() {
      lstPersons = new List<Person>();    
    }
}

public class Filter 
{
    public string Id { get; set; }
    public Operator Operator { get; set; }
    public string value { get; set; }
}

public void Main()
{
   //Get the json.
   //"Filters": [{"id": "Name","operator": "contains","value": "Microsoft"}]

    Filter Rules = JsonConvert.DeserializeObject<Filter>(json);

   // Get the list of person firstname.
    List<Person> lstPerson = GetFirstName();

   ParameterExpression param = Expression.Parameter(typeof(Person),"p");
   Expression exp = null;

   exp = GetExpression(param,rules[0]);

   //get all the name contains "john" or "John"
   var filteredCollection = lstPerson.Where(exp).ToList();

}

private Expression GetExpression(ParameterExpression param,Filter filter){
   MemberExpression member = Expression.Property(param,filter.Id);
   ConstantExpression constant = Expression.Constant(filter.value);

   Expression bEXP = null;

   switch (filter.Operator)
    {
         case Operator.contains:
           MethodInfo miContain = typeof(StringExts).getmethod("NewContains",BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Static);
           return  Expression.Call(miContain,member,constant,Expression.Constant(StringComparison.OrdinalIgnoreCase));; 
           break;
    }
 }

错误:

An unhandled exception of type ‘System.ArgumentException’ occurred in System.Core.dll.Additional information: Static method requires null instance,non-static method requires non-null instance.

如何调用miContain中的参数来跟随Call()方法?

我已经更新了守则.

解决方法

您没有指定所有参数.如果为所有人创建表达式,它可以工作:
ParameterExpression source = Expression.Parameter(typeof(string));
string Valtocheck = "A";
StringComparison StrComp = StringComparison.CurrentCultureIgnoreCase;

MethodInfo miContain = typeof(StringExts).getmethod("NewContains",BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Static);
var bEXP = Expression.Call(miContain,source,Expression.Constant(Valtocheck),Expression.Constant(StrComp));

var lambda = Expression.Lambda<Func<string,bool>>(bEXP,source);

bool b = lambda.Compile().Invoke("a");

ABAP mesh expression, JavaScript and Scala expression

ABAP mesh expression, JavaScript and Scala expression

ABAP Mesh expression

JavaScript

我在第10行调用了函数f,其中传入的第二个和第三个参数都是一个逗号表达式。
函数f的实现,会检查这两个参数的类型,如果是函数,则执行函数调用,再打印其返回值,否则直接打印传入的表达式的值。

执行上面这段代码,打印输出如下:

我们可以看出,虽然传入的第一个参数为true,导致函数f内部只会打印第二个参数y代表的表达式的值,5,但是第三个参数代表的表达式在函数f调用时,也进行了表达式求值,所以最后console也输出了Big calculation2。
如果我们想实现所谓的“惰性求值”,有时候也称”惰性计算“,那么只需要将原本写在表达式位置的逻辑用一个JavaScript函数包裹起来,如下:

再次调用f,此时传入的参数y和z的类型为函数,因此在f进行调用时,同之前传入的表达式不同,这里并不会即时调用y和z代表的函数。打印输出:

Scala

Scala 是一门多范式(multi-paradigm)的编程语言,设计初衷是要集成面向对象编程和函数式编程的各种特性。
Scala 运行在Java虚拟机上,并兼容现有的Java程序。
Scala 源代码被编译成Java字节码,所以它可以运行于JVM之上,并可以调用现有的Java类库。

下图第5行和第12行我分别定义了两个Scala函数exp_test1和exp_test2, 逻辑和之前的JavaScript函数f类似。
exp_test1接受的第二个和第三个参数类型为exp1 :=> Unit,意思是需要传入一个表达式,这个表达式的返回类型是Unit。
exp_test2接收的第二个和第三个参数类型为exp1() :=> Unit,意思是需要传入一个函数,这个函数没有任何输入参数,函数的返回类型是Unit。

第19行到第25行是对这两个函数的各种测试,打印输出:

可以看到,即使传入两个函数exp_test1和exp_test2的第二个和第三个参数都是表达式,Scala也能做到对表达式的惰性求值:
第19行和第20行的函数调用,第三个参数位置的表达式和函数都没有即时求值,而是惰性求值。
第22行和第23行的函数调用,第二个参数位置的表达式和函数都没有即时求值,而是惰性求值。

要获取更多Jerry的原创文章,请关注公众号"汪子熙":

ArcGis 字段计算器表达式(Field calculator expression).cal文件与标注表达式(label expression).lxp的实质及其编码方式、解析方法

ArcGis 字段计算器表达式(Field calculator expression).cal文件与标注表达式(label expression).lxp的实质及其编码方式、解析方法

ArcGis 字段计算器表达式可以保存为一个扩展名为.cal的文件,该文件的实质是一个文本文件,编码方式为 UTF-16-LE。

官方的说明是“ArcGIS 应用程序使用 UTF-16-LE 编码读写 .cal 文件。只要输出使用 UTF-16-LE 编码编写,其他应用程序(如记事本)可用于创建或修改 .cal 文件。使用任何其他编码将导致文件无法加载到代码段中。

在记事本编辑后保存时编码方式应选用Unicode。

在.net中读写应使用Encoding.Unicode。

例:

 1  string saveFilePath = Utils.PathUtil.ShowSaveFileDialog("ArcGis字段计算器表达式|*.cal|所有文件|*.*", ".cal");
 2                 if (saveFilePath != string.Empty)
 3                 {
 4                     StringBuilder stringBuilder = new StringBuilder();
 5                     stringBuilder.Append(this.rtxtCode.Text);
 6                     stringBuilder.AppendLine();
 7                     stringBuilder.Append("__esri_field_calculator_splitter__");
 8                     stringBuilder.AppendLine();
 9                     stringBuilder.Append(this.rtxtFunctionName.Text);
10                     System.IO.FileStream fileStream = new System.IO.FileStream(saveFilePath, FileMode.Create);
11                     StreamWriter streamWriter = new StreamWriter(fileStream,Encoding.Unicode);
12                     streamWriter.Write(stringBuilder);
13                     streamWriter.Flush();
14                     streamWriter.Close();
15                     streamWriter.Dispose();
16                     fileStream.Close();
17                 }

 在python下应使用“UTF-16-LE”

例:

cal=arcpy.GetParameterAsText(3)
    cal_cntent=codecs.open(cal,''r'',''utf-16-LE'')
    code=''''
    exp=''''
    line=cal_cntent.readline()
    while line:
        if ''__esri_field_calculator_splitter__'' not in line:
            if line !='' '':
                code+=line
        else:
            line=cal_cntent.readline()
            break
        line=cal_cntent.readline()
    while line:
        if line !='' '':
            exp+=line
        line=cal_cntent.readline()

 

编码方式自官方说明得之,链接附此:

https://pro.arcgis.com/zh-cn/pro-app/tool-reference/data-management/calculate-field.htm

.lxp与.cal同原理,不赘述。

asp.net-mvc – HTMLHelper,从属性中生成“Expression> expression”类型的参数

asp.net-mvc – HTMLHelper,从属性中生成“Expression> expression”类型的参数

我正在为编辑器编写 HTML Helper.我们的想法是使用属性AutoGenerateField从Model获取属性并构建一个表,其中每行包含一个字段的名称(也来自属性)和一个包含字段实际值的TextBox或CheckBox.

我有HTMLHelper的问题.由于我将整个模型发送给助手而不是一个值,因此我不能使用TextBoxFor等方法,因为它们需要参数,例如

"Expression<Func<TModel,TValue>> expression".

我正在使用反射,我尝试发送属性,但VisualStudio认为这是不正确的用法.

下面是我的HtmlHelper的简化方法:

public static MvcHtmlString GenerateEditor<TModel>(this HtmlHelper<TModel> htmlHelper)
{
    var model = htmlHelper.ViewData.Model;
    var result = String.Empty;

    //generating container,etc ...

    foreach (var property in model.GetType().GetProperties())
    {
        var attr = property.GetCustomAttributes(typeof (displayAttribute),true).FirstOrDefault(); 
        if (attr == null) continue;
        var autoGenerate = ((displayAttribute)attr).AutoGenerateField;
        if(autoGenerate)
        {
           //here I'm building the html string 
           //My problem is in the line below:
           var r = htmlHelper.TextBoxFor(property); 
        }
    }
    return MvcHtmlString.Create(result);
}

有任何想法吗?

解决方法

如何使用非lambda重载. :InputExtensions.TextBox()

if(autoGenerate)
{
   //here I'm building the html string 
   //My problem is in the line below:
   var r = htmlHelper.TextBox(property.Name); 
}
//not sure what you do with r from here...

如果我没有弄错,表单元素的name属性设置为属性名称,即使你使用函数的lambda版本,所以这应该做同样的事情.

我将尝试验证lambda函数的作用,您可能也可以这样做,因为您有TModel.

更新

从快速查看源代码内的事物InputExtensions.cs开始,TextBoxFor调用最终调用InputHelper(),最终调用ExpressionHelper.cs内的ExpressionHelper.GetExpressionText(LambdaExpression表达式),从粗略看起来的东西获取名称html属性的member.Name输入元素.

我现在无法完全验证它,因为我不在Windows上,但我认为非lambda函数应该适合您的需要.请告诉我它是怎么回事?

c – 有没有办法在使用clang的VisitCallExpr方法中获取CallExpr *的调用者?

c – 有没有办法在使用clang的VisitCallExpr方法中获取CallExpr *的调用者?

getDirectCallee()方法可以获取调用表达式的被调用者(称为方法/函数),但有没有办法在VisitCallExpr()方法中获取CallExpr *的调用者(调用它的方法/函数)?

有没有其他方法可以知道一个调用表达式的调用者?

解决方法

更好的方法是使用AST匹配器.
您基本上可以查找AST匹配器中的所有callExpr节点并绑定它们,同时绑定相应的调用方(CXXRecordDecl)节点以及不同的字符串.

例如:

CallBackFunc callBackFunc;

Matchers.addMatcher(callExpr(isExpansionInMainFile(),callee(),hasAncestor(recordDecl().bind("caller"))).bind("callee"),&callBackFunc);

然后在callBack函数中,您可以检索这些callee和caller函数,如下所示:

class CallBackFunc : public MatchFinder::MatchCallBack {
  public:
     virtual void run(const MatcherFinder::MatchResult &Results) {
        auto callee = Results.Nodes.getNodeAs<clang::CallExpr>("callee");
        auto caller = Results.Nodes.getNodeAs<clang::CXXRecordDecl>("caller"); 

       // Do what is required with callee and caller.
    }
};

(如果需要,我可以提供更多信息)

关于c# – 使用参数在expression.call中调用静态方法c#怎么调用静态方法的问题我们已经讲解完毕,感谢您的阅读,如果还想了解更多关于ABAP mesh expression, JavaScript and Scala expression、ArcGis 字段计算器表达式(Field calculator expression).cal文件与标注表达式(label expression).lxp的实质及其编码方式、解析方法、asp.net-mvc – HTMLHelper,从属性中生成“Expression> expression”类型的参数、c – 有没有办法在使用clang的VisitCallExpr方法中获取CallExpr *的调用者?等相关内容,可以在本站寻找。

本文标签: