Как преобразовать замыкание JScript в делегат .NET в JScript? - PullRequest
2 голосов
/ 24 февраля 2011

У меня есть цикл for, который должен преобразовывать вещи в тысячи файлов, которые не зависят друг от друга. Код написан на JScript. Я хотел бы добавить несколько потоков кода для распределения файлов между процессорами, так как другие, кажется, простаивают. Я пытаюсь использовать класс System.Threading.ThreadPool, в частности метод QueueUserWorkItem, в JScript, но во время выполнения выдает ошибку, которая говорит:

Unhandled Exception: System.InvalidCastException: Unable to cast object of type 'Microsoft.JScript.Closure' to type 'System.Threading.WaitCallback'.

Вот мой код:

var conv = function MyConverter(arg1)
{
    // do the work
};

ThreadPool.QueueUserWorkItem( WaitCallback(conv) );

Если я изменю свой код на «новый WaitCallback (conv)», я получу ошибку компилятора jsc.exe:

error JS1258: Delegates should not be explicitly constructed, simply use the method name

Итак, я попробовал это с:

ThreadPool.QueueUserWorkItem( conv );

Но затем мы вернулись к тому же исключению InvalidCastException выше.

1 Ответ

3 голосов
/ 24 февраля 2011

Проблема в том, что «глобальные» функции не могут использоваться в качестве делегатов таким образом. Это побочный эффект того факта, что созданные из них делегаты создаются с использованием:

Delegate.CreateDelegate( Type, Object, String )

Где второй параметр «Объект» - это экземпляр объекта, для которого будет вызван метод.

Вам нужно создать класс, чтобы делать то, что вы пытаетесь сделать, что-то вроде:

import System;
import System.Threading;

class MyConverterClass
{
    function QueueUserWorkItem()
    {
        return ThreadPool.QueueUserWorkItem(MyConverter);
    }

    function MyConverter()
    {
        print("Hello World.");
    }
}

// Example usage
var converter = new MyConverterClass();
converter.QueueUserWorkItem();
print("All done.");

Это должно скомпилироваться и работать нормально, я использовал JSC 10.00.30319 для проверки.

Вы можете использовать экземпляр класса для хранения любого состояния, которое вы планировали сохранить в замыкании (если оно есть), создав пару переменных экземпляра в классе.

Надеюсь, это поможет.

...