2012-09-05 98 views
0

我正在设计一个小线程框架,我希望线程框架尽可能地透明到最终代码,这样它几乎不会影响线性代码的语法。我已经想出了大部分的东西,但有些东西给我一个痒:如何定义一个参数,所以函数调用不会解决,直到我成功地将他们的上下文切换到一个新的线程?函数调用作为参数

的想法:

var myTask = new Transaction(); 
myTask < xyz.abc(); 
myTask < xyz.def(); 
...some more code... 
var result = waitfornext myTask; 

从本质上说,myTask会抢ABC()和高清()调用并将其管道到一个线程,则WAITFOR操作员将被阻塞,直到myTask的管道已完成和代码依赖于abc()和def()可以继续。以这种方式说出这个.Net的等待/异步模式,但是我想以我自己的方式重新执行它,因此它可以在所有.Net版本中使用,并可能移植到Java/XYZ语言。

问题:调用abc()和def()函数之前,编译器会将它们的返回值反馈给<运算符,但我真正想要的却是能够将这些函数调用提供给运营商,所以我可以推迟他们的执行,直到管道线程准备好这样做。

基本原理: 与async/await模型不同,您不必修改方法以使其可以异步化,并且无论如何都可以对事务方法使用任何方法。另一个优点是,擦除几条线,你的代码会回到线性状态(不是说异步模型没有这个优点,但它值得一提)

任何想法?

+1

代表? Lambda表达式?尽管如此,Task Parallel Library并没有什么? –

+0

我有我的动机,它已经存在的事实不应该阻止你想要重新创建它。 – Machinarius

+0

当你想要一个更好的车轮时,或者想更好地了解车轮的工作方式时,我完全无法重新发明车轮。你有一个非常不寻常/非C#的方法,但我不明白。 –

回答

1

不是传递xyz.abc()作为参数,这将在随后有评估的,而不是通过的东西,可以成为xyz.abc(),并修改目标的方法做 '变成':

变化

var evaluatedNow = SomeMethod(GetParameterValue()); 

... 

object SomeMethod(SomeType value) 
{ 
    // Do something with value 
} 

var evaluatedLater = SomeMethod(() => GetParameterValue()); 

... 

object SomeMethod(Func<SomeType> valueGetter) 
{ 
    SomeType value = valueGetter(); 
    // Do something with value 
} 
+0

我想知道那种系统,但我想我不得不迫使开发人员/用户将该方法包装在类中(类似java上的runnable)。有一个问题呢? Func会保存所有的参数吗?换句话说,is()=> xyz.abc(myParam)作为Func有效吗? – Machinarius

+0

如果编译器可以计算出你的意思(即它的范围),你不需要一个包装类。只要它具有正确的类型(所以任何返回正确类型的方法调用都可以),你可以在'=>后面使用任何表达式。 – AakashM

+1

请注意,'()=> xyz.abc(myParam)'捕获'myParam',即使它是一个值类型(例如整数),如果它在'Func'设置后更改,但在执行之前,它将是执行时使用的值。 –

1

撇开一个观察,即使用<操作符将参数提供给对象违背了临时读者的期望,您可以使用lambda表示您的函数。例如,Action,不返回值的代表,也可以使用这样的:

Action abs =() => xyz.abc(); // The() => syntax creates a delegate from a piece of code 
myTask.AddAction(abs); // Use a named function instead of operator `<` 
myTask.AddAction(() => xyz.def()); // You do not need a variable 
var result = myTask.Waitfornext(); 
+0

我知道它并不完全直观,但我的意图是让它包含更少的额外语法 – Machinarius

+1

这个答案不涉及额外的语法,你给出了一个新的含义。 –