Question

Je me demandais s'il était possible de compiler et exécuter du code stocké, sans générer un fichier EXE ou tout type d'autres fichiers, exécutez essentiellement le fichier de la mémoire.

En fait, l'application principale, aura un code stocké (code qui pourrait être changé), et il devra compiler le code et l'exécuter. sans créer de fichiers.

créer les fichiers, l'exécution du programme, puis de supprimer les fichiers ne sont pas une option. le code compilé devra être RAN de la mémoire.

exemples de code, ou des pointeurs, ou à peu près tout est le bienvenu:)

Était-ce utile?

La solution

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[] { });
}

Cette compile une classe simple de la chaîne de code source inclus, alors la classe instanciée et invoque pensivement ensuite une fonction.

Autres conseils

Voici un exemple de la façon d'utiliser System.Linq.Expressions ajouter à la réponse de Tim. Il est évident que ce n'est pas le plus joli code, mais avoir dans ce bel arbre comme forme rend le développement si facile.

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;
}

Il est possible. Il est facile ou difficile, selon la quantité et quel type de code que vous voulez écrire.

Modifier Notez que, avant .NET 4.0, System.Linq.Expressions se limite à ce que vous pouvez tenir sur une seule ligne de C #: qui est, pas si, alors que, l'affectation des variables etc

Oui, vous pouvez le faire. Il est très lent, mais vous pouvez certainement le faire. Regardez le CodeDOM ou (new CSharpCodeProvider().CreateCompiler()) en .Net.

Regardez dans System.CodeDom. Il fera exactement ce que vous recherchez.

En Mono vous utilisez CSharp.Evaluator. Il fonctionne vraiment dans la mémoire v. Certains des autres solutions a mentionné que écrire et lire dans un fichier sous le capot.

Aussi jeter un oeil à l'intégration d'un langage de script comme Python, Ruby, Lua, etc .. tous ceux qui soutien l'exécution du code de la mémoire sans rien écrit sur le disque.

Il est difficile, voire impossible, de compiler et exécuter C # sans créer un fichier, parce que ... Eh bien, c'est ce que la compilation est- transformer une langue dans un fichier exécutable. Qu'est-ce que vous cherchez est une sorte de fonctionnalité de script. Qu'est-ce que vous avez décrit dans votre question est essentiellement la différence entre un interprété langue et compilé langue. Voir Wikipedia:. Langage de script

En fonction de ce que vous allez utiliser cette fonction pour, vous pouvez faire grand usage d'un langage de script comme Python, Ruby ou Lua. Voici un exemple: Comment puis-je exécuter un script Python à partir de C # ?

Cela rendrait votre application dépend de python.exe (ou tout autre exécutable que vous auriez besoin pour exécuter le langage de script que vous choisissez). Si vous voulez éviter cela, il pourrait ne pas être trop difficile de faire votre propre langage de script que votre application ne l'exécution pour, en fonction de ce que vous devez faire avec votre script injecté.

Edit: Ce premier paragraphe est de la foutaise. Pardon. Voir http://msdn.microsoft.com /en-us/library/8ffc3x75%28v=vs.110%29.aspx

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top