编译并运行动态代码,而不生成EXE?

发布于 2024-09-08 02:19:09 字数 199 浏览 0 评论 0原文

我想知道是否可以编译并运行存储的代码,而不生成 exe 或任何类型的其他文件,基本上从内存运行该文件。

基本上,主应用程序将具有一些存储的代码(可能会更改的代码),并且需要编译代码并执行它。无需创建任何文件。

创建文件,运行程序,然后删除文件不是一个选项。编译后的代码需要从内存中运行。

代码示例,或指针,或几乎任何东西都是受欢迎的:)

I was wondering if it was possible to compile, and run stored code, without generating an exe or any type of other files, basically run the file from memory.

Basically, the Main application, will have some stored code (code that will potentially be changed), and it will need to compile the code, and execute it. without creating any files.

creating the files, running the program, and then deleting the files is not an option. the compiled code will need to be ran from memory.

code examples, or pointers, or pretty much anything is welcome :)

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(8

终难愈 2024-09-15 02:19:09
using (Microsoft.CSharp.CSharpCodeProvider foo = 
           new Microsoft.CSharp.CSharpCodeProvider())
{
    var res = foo.CompileAssemblyFromSource(
        new System.CodeDom.Compiler.CompilerParameters() 
        {  
            GenerateInMemory = true 
        }, 
        "public class FooClass { public string Execute() { return \"output!\";}}"
    );

    var type = res.CompiledAssembly.GetType("FooClass");

    var obj = Activator.CreateInstance(type);

    var output = type.GetMethod("Execute").Invoke(obj, new object[] { });
}

这会根据包含的源代码字符串编译一个简单的类,然后实例化该类并反射性地调用其上的函数。

using (Microsoft.CSharp.CSharpCodeProvider foo = 
           new Microsoft.CSharp.CSharpCodeProvider())
{
    var res = foo.CompileAssemblyFromSource(
        new System.CodeDom.Compiler.CompilerParameters() 
        {  
            GenerateInMemory = true 
        }, 
        "public class FooClass { public string Execute() { return \"output!\";}}"
    );

    var type = res.CompiledAssembly.GetType("FooClass");

    var obj = Activator.CreateInstance(type);

    var output = type.GetMethod("Execute").Invoke(obj, new object[] { });
}

This compiles a simple class from the source code string included, then instantiates the class and reflectively invokes a function on it.

回眸一笑 2024-09-15 02:19:09

以下是如何使用 System.Linq.Expressions 添加到 Tim 的答案的示例。显然,它不是最漂亮的代码,但以这种漂亮的树状形式使开发变得如此简单。

private  Expression<IsWordChar> CreateIsWordCharExpression()
{
    var e = Expression.Parameter(typeof(int), "e");
    var c = Expression.Variable(typeof(char), "c");
    var returnLabel = Expression.Label(Expression.Label(typeof(bool)), _falseConstant);
    var lambda = Expression.Lambda<IsWordChar>(
        Expression.Block(
            new[] { c },
            Expression.IfThen(
                Expression.OrElse(
                    Expression.Equal(e, Expression.Constant(-1)),
                    Expression.Equal(e, _inputLengthVar)
                ),
                Expression.Return(returnLabel.Target, _falseConstant)
            ),
            Expression.Assign(c, Expression.MakeIndex(_str, _stringCharsPropertyInfo, new[] { e })),
            Expression.IfThenElse(
                Expression.OrElse(
                    Expression.OrElse(
                        Expression.OrElse(
                            Expression.AndAlso(
                                Expression.GreaterThanOrEqual(c, Expression.Constant('a')),
                                Expression.LessThanOrEqual(c, Expression.Constant('z'))
                            ),
                            Expression.AndAlso(
                                Expression.GreaterThanOrEqual(c, Expression.Constant('A')),
                                Expression.LessThanOrEqual(c, Expression.Constant('Z'))
                            )
                        ),
                        Expression.AndAlso(
                            Expression.GreaterThanOrEqual(c, Expression.Constant('0')),
                            Expression.LessThanOrEqual(c, Expression.Constant('1'))
                        )
                    ),
                    Expression.Equal(c, Expression.Constant('_'))
                ),
                Expression.Return(returnLabel.Target, _trueConstant),
                Expression.Return(returnLabel.Target, _falseConstant)
            ),
            returnLabel
        ),
        "IsWordChar",
        new[] { e }
    );
    return lambda;
}

Here is an example of how to use System.Linq.Expressions to add to Tim's answer. Obviously it isn't the prettiest code but having it in this nice tree-like form makes development so easy.

private  Expression<IsWordChar> CreateIsWordCharExpression()
{
    var e = Expression.Parameter(typeof(int), "e");
    var c = Expression.Variable(typeof(char), "c");
    var returnLabel = Expression.Label(Expression.Label(typeof(bool)), _falseConstant);
    var lambda = Expression.Lambda<IsWordChar>(
        Expression.Block(
            new[] { c },
            Expression.IfThen(
                Expression.OrElse(
                    Expression.Equal(e, Expression.Constant(-1)),
                    Expression.Equal(e, _inputLengthVar)
                ),
                Expression.Return(returnLabel.Target, _falseConstant)
            ),
            Expression.Assign(c, Expression.MakeIndex(_str, _stringCharsPropertyInfo, new[] { e })),
            Expression.IfThenElse(
                Expression.OrElse(
                    Expression.OrElse(
                        Expression.OrElse(
                            Expression.AndAlso(
                                Expression.GreaterThanOrEqual(c, Expression.Constant('a')),
                                Expression.LessThanOrEqual(c, Expression.Constant('z'))
                            ),
                            Expression.AndAlso(
                                Expression.GreaterThanOrEqual(c, Expression.Constant('A')),
                                Expression.LessThanOrEqual(c, Expression.Constant('Z'))
                            )
                        ),
                        Expression.AndAlso(
                            Expression.GreaterThanOrEqual(c, Expression.Constant('0')),
                            Expression.LessThanOrEqual(c, Expression.Constant('1'))
                        )
                    ),
                    Expression.Equal(c, Expression.Constant('_'))
                ),
                Expression.Return(returnLabel.Target, _trueConstant),
                Expression.Return(returnLabel.Target, _falseConstant)
            ),
            returnLabel
        ),
        "IsWordChar",
        new[] { e }
    );
    return lambda;
}
凉月流沐 2024-09-15 02:19:09

这是有可能的。这或容易或困难,取决于您要编写的代码数量和类型。

编辑:请注意,在 .NET 4.0 之前,System .Linq.Expressions 仅限于单行 C# 中可以容纳的内容:即,没有 if、while、变量赋值等。

It's possible. It's easy or hard, depending on how much and what kind of code you want to write.

Edit: Note that, prior to .NET 4.0, System.Linq.Expressions is limited to what you can fit on a single line of C#: that is, no if, while, variable assignment etc.

蓝颜夕 2024-09-15 02:19:09

是的,你可以这样做。虽然速度很慢,但你一定可以做到。查看 .Net 中的 CodeDOM 或 (new CSharpCodeProvider().CreateCompiler())

Yes, you can do this. It is very slow, but you can certainly do it. Look at the CodeDOM or the (new CSharpCodeProvider().CreateCompiler()) in .Net.

不即不离 2024-09-15 02:19:09

查看System.CodeDom。它会完全满足您的需求。

Look into System.CodeDom. It will do exactly what you are looking for.

征﹌骨岁月お 2024-09-15 02:19:09

在 Mono 中,您使用 CSharp.Evaluator。它真正在内存中工作,与提到的一些其他解决方案相比,这些解决方案在后台的文件中写入和读回。

In Mono you use CSharp.Evaluator. It works truly in memory v. some of the other solutions mentioned that write out and read back in a file under the hood.

女中豪杰 2024-09-15 02:19:09

还要看看嵌入的脚本语言,如 Python、Ruby、Lua 等。所有这些都支持从内存执行代码,而不需要将任何内容写入磁盘。

Also take a look at embedding a scripting language like Python, Ruby, Lua, etc.. all of those support executing code from memory without anything being written to the disk.

青巷忧颜 2024-09-15 02:19:09

在不创建文件的情况下编译和执行 C# 即使不是不可能,也是很困难的,因为……嗯,这就是编译的意义 - 将语言转换为可执行文件。您正在寻找的是某种脚本功能。您在问题中所描述的本质上是解释语言和编译语言之间的区别。请参阅维基百科:脚本语言

取决于您将使用此功能的用途因为,您可以充分利用 Python、Ruby 或 Lua 等脚本语言。下面是一个示例:如何从 C# 运行 Python 脚本?

这将使您的应用程序依赖于 python.exe(或运行您选择的脚本语言所需的任何可执行文件)。如果您想避免这种情况,那么创建您自己的脚本语言(供您的应用程序执行运行时)可能并不难,具体取决于您需要对注入的脚本执行什么操作。

编辑:第一段是垃圾。对不起。请参阅 http://msdn.microsoft.com /en-us/library/8ffc3x75%28v=vs.110%29.aspx

It's difficult, if not impossible to compile and execute C# without creating a file, because... Well, that's what compilation is- turning a language into an executable file. What you're looking for is some kind of scripting functionality. What you described in your question is essentially the difference between an interpreted language and a compiled language. See Wikipedia: Scripting language.

Depending on what you'll be using this feature for, you could make great use of a scripting language like Python, Ruby, or Lua. Here's an example: How do I run a Python script from C#?

This would make your application dependant upon python.exe (or whatever executable you'd need to run the scripting language you choose). If you want to avoid that, it might not be too hard to make your own scripting language that your application does the runtime for, depending on what you need to do with your injected script.

Edit: That first paragraph is rubbish. Sorry. See http://msdn.microsoft.com/en-us/library/8ffc3x75%28v=vs.110%29.aspx

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文