编写符合模板定义函数原型的函数
Writing functions conforming template defined function prototypes
令我非常高兴的是,我发现 D 已经取得了进步,现在实际上可以在 Windows 64 位上运行。它甚至有一个 Visual Studio 集成,在我玩了几个小时的新玩具后,据我所知似乎可以正常工作。
所以,显然我刚刚开始将 D 作为一种语言来玩,并且是 D 中该死的新手。
在下面的代码中,我的目标是在模板中定义函数原型,然后将函数编写为符合这些原型的 main() 的子函数。但是编译器抱怨,现在我找不到正确的方法(可能是简单的语法问题)。
我得到的编译器错误是:
main.d(90): Error: function main.Actor!(int, int).Worker (Duration timeout, bool function(int) timeoutHandler, bool function(int, int) messageHandler, int context) is not callable using argument types ()
main.d(90): Error: function main.main.W1OnTimeout (int context) is not callable using argument types ()
main.d(90): Error: function main.main.W1OnMessage (int context, int message) is not callable using argument types ()
Building Debug\ConsoleApp1.exe failed!
import std.stdio;
import core.time;
import std.socket;
import std.concurrency;
import core.thread;
enum SystemMessage
{
Shutdown,
Terminate,
Ping,
Enable,
Disable
}
template Actor(C,M)
{
// TimeoutHandler implementations always return true
// unless the worker shall terminate.
alias TimeoutHandler = bool function(C);
// MessageHandler implementations always return true
// unless the worker shall terminate.
alias MessageHandler = bool function(C,M);
void
Worker
( Duration timeout
, TimeoutHandler timeoutHandler
, MessageHandler messageHandler
, C context
)
{
bool running = true;
bool enabled = true;
while(running)
{
if( true == std.concurrency.receiveTimeout
(timeout,
(M message)
{
if(enabled)
{
if(!messageHandler(context,message) )
{
running = false;
}
}
},
(SystemMessage message)
{
switch(message)
{
case SystemMessage.Shutdown: running = false; break;
case SystemMessage.Terminate: running = false; break;
case SystemMessage.Enable: enabled = true; break;
case SystemMessage.Disable: enabled = false; break;
case SystemMessage.Ping: /* TODO: supervisor... */; break;
default: break;
}
}
))
{
}
else
{
if(!timeoutHandler(context))
{
running = false;
}
}
}
}
}
alias IntIntActor = Actor!(int,int);
int main(string[] argv)
{
// The signatures of the next 2 functions conform to the function
// declarations, given in Actor template (IntIntActor).
// How to write them so it works?
bool W1OnTimeout(int context)
{
writeln("W1OnTimeout()");
return true;
}
bool W1OnMessage(int context,int message)
{
writefln("W1OnMessage: context = %d, message = %d", context, message);
return true;
}
// Do I need some special syntax here? Like e.g. &W1OnTimeout ? Or a cast?
auto w1 = spawn(IntIntActor.Worker,1000.msecs,W1OnTimeout,W1OnMessage,1);
for(int i = 0; i < 10; i++)
{
send(w1,i);
}
Thread.sleep(5000.msecs);
send(w1,SystemMessage.Shutdown);
thread_joinAll();
return 0;
}
提前感谢您的帮助!
您在评论中几乎给出了答案:
// Do I need some special syntax here? Like e.g. &W1OnTimeout ? Or a cast?
&W1OnTimeout
就是这样;还有 &IntIntActor.Worker
和 &W1OnMessage
.
仍然无法编译,因为&W1OnTimeout
和&W1OnMessage
被视为委托,但Worker
接受函数指针。标记嵌套函数 static
并且有效:
static bool W1OnTimeout(int context)
{
...
}
static bool W1OnMessage(int context,int message)
{
...
}
或者,在 main 之外定义它们。
令我非常高兴的是,我发现 D 已经取得了进步,现在实际上可以在 Windows 64 位上运行。它甚至有一个 Visual Studio 集成,在我玩了几个小时的新玩具后,据我所知似乎可以正常工作。
所以,显然我刚刚开始将 D 作为一种语言来玩,并且是 D 中该死的新手。
在下面的代码中,我的目标是在模板中定义函数原型,然后将函数编写为符合这些原型的 main() 的子函数。但是编译器抱怨,现在我找不到正确的方法(可能是简单的语法问题)。
我得到的编译器错误是:
main.d(90): Error: function main.Actor!(int, int).Worker (Duration timeout, bool function(int) timeoutHandler, bool function(int, int) messageHandler, int context) is not callable using argument types ()
main.d(90): Error: function main.main.W1OnTimeout (int context) is not callable using argument types ()
main.d(90): Error: function main.main.W1OnMessage (int context, int message) is not callable using argument types ()
Building Debug\ConsoleApp1.exe failed!
import std.stdio;
import core.time;
import std.socket;
import std.concurrency;
import core.thread;
enum SystemMessage
{
Shutdown,
Terminate,
Ping,
Enable,
Disable
}
template Actor(C,M)
{
// TimeoutHandler implementations always return true
// unless the worker shall terminate.
alias TimeoutHandler = bool function(C);
// MessageHandler implementations always return true
// unless the worker shall terminate.
alias MessageHandler = bool function(C,M);
void
Worker
( Duration timeout
, TimeoutHandler timeoutHandler
, MessageHandler messageHandler
, C context
)
{
bool running = true;
bool enabled = true;
while(running)
{
if( true == std.concurrency.receiveTimeout
(timeout,
(M message)
{
if(enabled)
{
if(!messageHandler(context,message) )
{
running = false;
}
}
},
(SystemMessage message)
{
switch(message)
{
case SystemMessage.Shutdown: running = false; break;
case SystemMessage.Terminate: running = false; break;
case SystemMessage.Enable: enabled = true; break;
case SystemMessage.Disable: enabled = false; break;
case SystemMessage.Ping: /* TODO: supervisor... */; break;
default: break;
}
}
))
{
}
else
{
if(!timeoutHandler(context))
{
running = false;
}
}
}
}
}
alias IntIntActor = Actor!(int,int);
int main(string[] argv)
{
// The signatures of the next 2 functions conform to the function
// declarations, given in Actor template (IntIntActor).
// How to write them so it works?
bool W1OnTimeout(int context)
{
writeln("W1OnTimeout()");
return true;
}
bool W1OnMessage(int context,int message)
{
writefln("W1OnMessage: context = %d, message = %d", context, message);
return true;
}
// Do I need some special syntax here? Like e.g. &W1OnTimeout ? Or a cast?
auto w1 = spawn(IntIntActor.Worker,1000.msecs,W1OnTimeout,W1OnMessage,1);
for(int i = 0; i < 10; i++)
{
send(w1,i);
}
Thread.sleep(5000.msecs);
send(w1,SystemMessage.Shutdown);
thread_joinAll();
return 0;
}
提前感谢您的帮助!
您在评论中几乎给出了答案:
// Do I need some special syntax here? Like e.g. &W1OnTimeout ? Or a cast?
&W1OnTimeout
就是这样;还有 &IntIntActor.Worker
和 &W1OnMessage
.
仍然无法编译,因为&W1OnTimeout
和&W1OnMessage
被视为委托,但Worker
接受函数指针。标记嵌套函数 static
并且有效:
static bool W1OnTimeout(int context)
{
...
}
static bool W1OnMessage(int context,int message)
{
...
}
或者,在 main 之外定义它们。