简单翻译go到d

go的多任务好,但不完美.语法简单,强大抽象.如果你腻了.试试d.
d支持纤程,但仅单线程.但有库jin.go.
原文在此

unittest
{
    import core.time;
    import std.range;
    import jin.go;
    
    __gshared static string[] log;
    
    static void saying(string message){//必须是静
        foreach( _ ; 3.iota ){
            sleep( 100.msecs);
            log ~= message;
        }
    }//没访问本地变量
    
    go!saying( "hello" );
    sleep( 50.msecs );
    saying( "world" );
    
    log.assertEq([ "hello" , "world" , "hello" , "world" , "hello" , "world" ]);
}

unittest{//无等待栈
    import jin.go;
    
    auto numbers = new Channel!int(2);
    numbers.next = 1;
    numbers.next = 2;//next不如<-方便
    numbers.next.assertEq( 1 );
    numbers.next.assertEq( 2 );
    //手动监控,读写不能超过一个
    //通道大小512字节
}
unittest
{
    import std.algorithm;
    import std.range;
    import jin.go;
    
    static auto summing( Channel!int sums , const int[] numbers ) {
        sums.next = numbers.sum;//标准算法,要实现区间接口
    }
    
    immutable int[] numbers = [ 7 , 2 , 8 , -9 , 4 , 0 ];
    
    Inputs!int sums;//这个,从每个注册的非空频道读
    go!summing(sums.make(1),numbers[0 .. $/2 ] );
    go!summing(sums.make(1),numbers[$/2 .. $ ] );//不变数组,并行
    auto res = sums.take(2).array;//取.
    
    ( res ~ res.sum ).assertEq([ 17 , -5 , 12 ]);
}//go.d非阻塞.你必须建一个通信通道,
//为了方便,建立<平衡器输入和输出>.
unittest
{
    import std.range;
    import jin.go;
  
    static auto fibonacci( Channel!int numbers , int count )
    {
        auto range = recurrence!q{ a[n-1] + a[n-2] }( 0 , 1 ).take( count );
        foreach( x ; range ) numbers.next = x;
        numbers.close();
    }
    
    auto numbers = new Channel!int(10);
    go!fibonacci( numbers , numbers.size );
    
    numbers.array.assertEq([ 0 , 1 , 1 , 2 , 3 , 5 , 8 , 13 , 21 , 34 ]);
}
//化简为:
unittest
{
    import std.range;
    import jin.go;
    
    static auto fibonacci( int limit ){
        return recurrence!q{ a[n-1] + a[n-2] }( 0 , 1 ).take( limit );
    }//recurrence->再现
    
    fibonacci( 10 ).array.assertEq([ 0 , 1 , 1 , 2 , 3 , 5 , 8 , 13 , 21 , 34 ]);
    go!fibonacci( 10 ).array.assertEq([ 0 , 1 , 1 , 2 , 3 , 5 , 8 , 13 , 21 , 34 ]);
}
unittest
{
    import std.range;
    import jin.go;
    
    __gshared int[] log;
    
    static auto fibonacci( Channel!int numbers , Channel!bool control )
    {
        auto range = recurrence!q{ a[n-1] + a[n-2] }( 0 , 1 );
    
        while( !control.closed )
        {
            if( numbers.needed ) numbers.next = range.next;
            yield;
        }
    
        log ~= -1;
        numbers.close();
    }
    
    static void print( Channel!bool control , Channel!int numbers )
    {
        foreach( i ; 10.iota ) log ~= numbers.next;
        control.close();
    }
    
    auto numbers = new Channel!int(1);
    auto control = new Channel!bool(1);
    
    go!print( control , numbers );
    go!fibonacci( numbers , control );
    
    while( !control.empty || !numbers.empty ) yield;
    
    log.assertEq([ 0 , 1 , 1 , 2 , 3 , 5 , 8 , 13 , 21 , 34 , -1 ]);
}
unittest
{
    import core.time;
    import jin.go;
  
    static auto after( Channel!bool channel , Duration dur )
    {
        sleep( dur );
        if( !channel.closed ) channel.next = true;
    }
    
    static auto tick( Channel!bool channel , Duration dur )
    {
        while( !channel.closed ) after( channel , dur );
    }
    
    auto ticks = go!tick( 101.msecs );
    auto booms = go!after( 501.msecs );
    
    string log;
    
    while( booms.clear )
    {
        while( !ticks.clear ) {
            log ~= "tick";
            ticks.popFront;
        }
        log ~= ".";
        sleep( 51.msecs );
    }
    log ~= "BOOM!";
    
    log.assertEq( "..tick..tick..tick..tick..BOOM!" );
}//很多看不懂了.
unittest
{
    import core.atomic;
    import core.time;
    import std.range;
    import std.typecons;
    import jin.go;
    
    synchronized class SafeCounter
    {//同步类告诉你,建了个锁
        private int[string] store;
    
        void inc( string key )
        {
            ++ store[key];
        }
    
        auto opIndex( string key )
        {
            return store[ key ];
        }
        void opIndexUnary( string op = "++" )( string key )
        {
            this.inc( key );
        }
    }//危险的是`模板方法不在互斥锁内`.
//实现了个`inc`.实现难看,但好用
    
    static counter = new shared SafeCounter;
//可安全传递,可直接在不同的流中使用
    
    static void working( int i )
    {
        ++ counter["somekey"];
    }
    
    foreach( i ; 1000.iota ) {
        go!working( i );
    }
    
    sleep( 1.seconds );
    
    counter["somekey"].assertEq( 1000 );
}
posted @   zjh6  阅读(12)  评论(0编辑  收藏  举报  
编辑推荐:
· AI与.NET技术实操系列:基于图像分类模型对图像进行分类
· go语言实现终端里的倒计时
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
阅读排行:
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· ollama系列01:轻松3步本地部署deepseek,普通电脑可用
· 25岁的心里话
· 按钮权限的设计及实现
点击右上角即可分享
微信分享提示