문제

나는 Python으로 클래스를 작성하여 Ironpython을 통해 .NET 어셈블리로 포장하고 C# 응용 프로그램에 인스턴스화하려는 클래스를 작성했습니다. 수업을 Ironpython으로 마이그레이션하고 도서관 어셈블리를 만들어 참조했습니다. 이제 실제로 해당 수업의 인스턴스를 어떻게 얻습니까?

수업은 다음과 같이 (부분적으로) 보입니다.

class PokerCard:
    "A card for playing poker, immutable and unique."

    def __init__(self, cardName):

내가 C#에 쓴 테스트 스텁은 다음과 같습니다.

using System;

namespace pokerapp
{
    class Program
    {
        static void Main(string[] args)
        {
            var card = new PokerCard(); // I also tried new PokerCard("Ah")
            Console.WriteLine(card.ToString());
            Console.ReadLine();
        }
    }
}

C#에서이 클래스를 인스턴스화하기 위해 무엇을해야합니까?

도움이 되었습니까?

해결책

Ironpython 클래스입니다 ~ 아니다 .NET 클래스. 그들은 Python metaclass 인 ironpython.runtime.types.pythontype의 인스턴스입니다. 이는 파이썬 클래스가 동적이며 런타임에 메소드의 추가 및 제거, .NET 클래스에서는 할 수없는 일이 있기 때문입니다.

C#에서 Python 클래스를 사용하려면 ObjectOperations 클래스를 사용해야합니다. 이 클래스를 사용하면 언어 자체의 의미론에서 파이썬 유형과 인스턴스에서 작동 할 수 있습니다. 예를 들어, 적절한 경우 마법의 방법을 사용하고 자동 프로모션 정수를 길게 사용합니다. 소스를 보거나 반사기를 사용하여 객체 요법에 대해 자세히 알아볼 수 있습니다.

여기 예입니다. Calculator.py는 간단한 클래스를 포함합니다.

class Calculator(object):
    def add(self, a, b):
        return a + b

다음과 같은 프리 .NET 4.0 C# 코드에서 사용할 수 있습니다.

ScriptEngine engine = Python.CreateEngine();
ScriptSource source = engine.CreateScriptSourceFromFile("Calculator.py");
ScriptScope scope = engine.CreateScope();

ObjectOperations op = engine.Operations;

source.Execute(scope); // class object created
object klaz = scope.GetVariable("Calculator"); // get the class object
object instance = op.Call(klaz); // create the instance
object method = op.GetMember(instance, "add"); // get a method
int result = (int)op.Call(method, 4, 5); // call method and get result (9)

어셈블리 Ironpython.dll, Microsoft.scripting 및 Microsoft.scripting.core를 참조해야합니다.

C# 4는 이것을 훨씬 쉽게 만들었습니다 새로운 동적 유형.

ScriptEngine engine = Python.CreateEngine();
ScriptSource source = engine.CreateScriptSourceFromFile("Calculator.py");
ScriptScope scope = engine.CreateScope();
source.Execute(scope);

dynamic Calculator = scope.GetVariable("Calculator");
dynamic calc = Calculator();
int result = calc.add(4, 5);

NUGET 지원과 함께 Visual Studio 2010 이상을 사용하는 경우 적절한 라이브러리를 다운로드하고 참조하기 위해이를 실행하십시오.

Install-Package IronPython

다른 팁

이제 .NET 4.0이 릴리스되고 동적 유형이 있으므로이 예제를 업데이트해야합니다. M-SHARP의 원래 답변에서와 동일한 Python 파일 사용 :

class Calculator(object):
    def add(self, a, b):
        return a + b

.NET 4.0을 사용하여 호출하는 방법은 다음과 같습니다.

string scriptPath = "Calculator.py";
ScriptEngine engine = Python.CreateEngine();
engine.SetSearchPaths(new string[] {"Path to your lib's here. EG:", "C:\\Program Files (x86)\\IronPython 2.7.1\\Lib"});
ScriptSource source = engine.CreateScriptSourceFromFile(scriptPath);
ScriptScope scope = engine.CreateScope();
ObjectOperations op = engine.Operations;
source.Execute(scope);

dynamic Calculator = scope.GetVariable("Calculator");
dynamic calc = Calculator();
return calc.add(x,y);          

다시 말하지만 Ironpython.dll 및 Microsoft.scripting에 대한 참조를 추가해야합니다.

보시다시피 소스 파일의 초기 설정 및 작성은 동일합니다.

그러나 일단 소스가 성공적으로 실행되면, 새로운 "동적"키워드 덕분에 Python 기능으로 작업하는 것이 훨씬 쉽습니다.

Clever Human이 .py 파일의 Ironpython 소스 코드 대신 Compiled Ironpython 클래스 (DLL)를 위해 제공 한 위의 예를 업데이트하고 있습니다.

# Compile IronPython calculator class to a dll
clr.CompileModules("calculator.dll", "calculator.py")

새로운 동적 유형의 C# 4.0 코드는 다음과 같습니다.

// IRONPYTHONPATH environment variable is not required. Core ironpython dll paths should be part of operating system path.
ScriptEngine pyEngine = Python.CreateEngine();
Assembly myclass = Assembly.LoadFile(Path.GetFullPath("calculator.dll"));
pyEngine.Runtime.LoadAssembly(myclass);
ScriptScope pyScope = pyEngine.Runtime.ImportModule("calculator");
dynamic Calculator = pyScope.GetVariable("Calculator");
dynamic calc = Calculator();
int result = calc.add(4, 5);

참조 :

  1. .NET/CSHARP IP 2.6에서 컴파일 된 파이썬 클래스 사용
  2. Ironpython 스크립트의 정적 편집

나는 높고 낮은 검색을했으며 이것과 관련된 많은 정보가없는 것 같습니다. 나는 아무도 당신이 원하는 깨끗한 방식으로 이것을 할 수있는 방법을 고안하지 않았다고 확신합니다.

이것이 문제라고 생각하는 주된 이유는 PokerCard C# 응용 프로그램을 입력하십시오. 파이썬 코드를 IL로 컴파일해야합니다. 나는 파이썬이 있다고 생각하지 않습니다->IL 컴파일러가 있습니다.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top