Darrell Hawley: Home Page

Wednesday, February 04, 2009

Note to Self 8 - IronPython2, Hosting, DLR

  • The latest DLR code and documentation can be found at www.codeplex.com/dlr
  • For the examples below, here is the Python script I'm using
  • class Person(object):
        def __init__(self, name, phone):
            self.name = name
            self.phone = phone
        def TalkToCSharp(self):
            val = {"name":self.name, "phone":self.phone}
            return val

     

    def GetPerson():
        person = Person("darrell", "555-4321")
        return person.TalkToCSharp()

    def GetPersonWithParams(name, phone):
        person = Person(name, phone)
        return person.TalkToCSharp()

    theNumberFive = 5
    myPerson = GetPerson()

  • Simplest thing you can do is execute a Python script.

  • static void ExecutePythonScript(string path)
    {
        ScriptRuntime runtime = Python.CreateRuntime();
        runtime.ExecuteFile(path);
    }

  • Sometimes you need to get a variable after a script has run.
  • static void GetDoubleVariable(string path)
    {
        ScriptRuntime runtime = Python.CreateRuntime();
        ScriptScope scope = runtime.ExecuteFile(path);
        object x = scope.GetVariable("theNumberFive");
        Console.WriteLine(x);
    }

  • What happens if you're trying to return a custom class defined in the script? The easiest - and IMHO the best - way to go about this is to convert the object to a dictionary before passing it to your C# code.
  • static void GetInstanceCustomClass(string path)
    {
        ScriptRuntime runtime = Python.CreateRuntime();
        ScriptScope scope = runtime.ExecuteFile(path);
        PythonDictionary dictionary =
            scope.GetVariable("myPerson")
            as PythonDictionary;
        foreach (var property in dictionary)
            Console.WriteLine(property.Key +
                " == " + property.Value);
    }

  • Getting properties is definitely useful, but you'll probably want to call a function.
  • static void CallingAFunction(string path)
    {
        ScriptRuntime runtime = Python.CreateRuntime();
        ScriptScope scope = runtime.ExecuteFile(path);
        ObjectOperations op =
            scope.Engine.CreateOperations();
        ObjectHandle handle =
            scope.GetVariableHandle("GetPerson");
        var x = op.Call(handle, new object[0]);
        PythonDictionary dictionary =
            x.Unwrap() as PythonDictionary;
        foreach (var property in dictionary)
            Console.WriteLine(property.Key +
                " == " + property.Value);
    }

  • Here's an example of passing parameters to a Python function.
  • static void CallingAFunctionWithParameters(string path)
    {
        ScriptRuntime runtime = Python.CreateRuntime();
        ScriptScope scope = runtime.ExecuteFile(path);
        ObjectOperations op =
            scope.Engine.CreateOperations();
        ObjectHandle handle =
            scope.GetVariableHandle("GetPersonWithParams");
        var x = op.Call(handle, "Larry", "555-1234");
        PythonDictionary dictionary =
            x.Unwrap() as PythonDictionary;
        foreach (var property in dictionary)
            Console.WriteLine(property.Key +
                " == " + property.Value);
    }

Labels: , , , ,

1 Comments:

  • If you don't want to bother creating dictionaries for each of your objects by hand then you should take a look at the jsonpickle module.

    You don't even have to use the json part. jsonpickle.encoder provides a flatten() method that can convert any python object into a simple dictionary.

    By Blogger David, at Fri Apr 10, 03:38:00 PM  

Post a Comment

<< Home