MapReduce API | Ignite文档

点燃2023年峰会-按需观看-立即注册!

编辑

MapReduce API

概述

Ignite提供了一个用于执行简化MapReduce操作的API。MapReduce模式基于以下假设:想要执行的任务可以分为多个作业(映射阶段),其中每个作业单独执行。每个作业产生的结果是聚合成最终结果(还原阶段)。

在像Ignite这样的分布式系统中,作业分布在根据预配置的节点负载平衡策略并在提交任务的节点上聚合结果。

MapReduce模式由计算任务接口。

注释

使用计算任务只有当您需要对作业到节点映射或自定义故障切换逻辑。对于所有其他情况,您应该使用简单闭包.

了解计算任务接口

这个计算任务接口提供了一种实现自定义映射和reduce逻辑的方法。该接口有三种方法:地图(…),结果()、和减少().

这个地图()应该实现方法来基于输入参数创建计算作业,并将其映射到工作节点。该方法接收要在其上运行任务的集群节点的集合以及任务的输入参数。该方法返回一个映射,其中作业作为键,映射的工作节点作为值。然后将作业发送到映射的节点并在那里执行。

这个结果()方法在每个作业完成后调用,并返回计算作业结果策略指示如何继续执行任务。该方法接收作业的结果以及迄今为止收到的所有作业结果的列表。该方法可以返回以下值之一:

  • 等待-等待所有剩余作业完成(如果有);

  • 减少-立即转到reduce步骤,丢弃所有剩余的作业和尚未收到的结果;

  • 故障切换-将作业故障转移到另一个节点(请参阅容错性).

这个减少()方法在reduce步骤中调用,此时所有作业都已完成(或结果()方法返回了减少特定作业的结果策略)。该方法接收包含所有已完成结果的列表,并返回计算的最终结果。

执行计算任务

要执行计算任务,请调用点火计算执行(…)方法并将计算任务的输入参数作为最后一个参数传递。

点燃 点燃 = 点火.开始();

点火计算 计算 = 点燃.计算();

整数 计数 = 计算.执行(新的 字符计数任务(), “Hello Grid Enabled World!”);
 字符计数计算作业 : ICompute作业<整数>
{
    私有的 只读的 一串 _参数;

    公众的 字符计数计算作业(一串 参数)
    {
        慰问.WriteLine(写入行)(“>>>打印” + 参数 + “”来自计算作业。“);
        ._参数 = 参数;
    }

    公众的 整数 执行()
    {
        返回 _参数.长度;
    }

    公众的 空隙 取消()
    {
         新的 系统.未实现异常();
    }
}


 字符计数任务 : IComputeTask(计算任务)<一串, 整数, 整数>
{
    公众的 IDictionary(图片)<ICompute作业<整数>, ICluster节点> 地图(IL列表<ICluster节点> 次网格, 一串 参数)
    {
        无功功率,无功功率 地图 = 新的 字典<ICompute作业<整数>, IC集群节点>();
        使用 (无功功率,无功功率 枚举器 = 次网格.方法())
        {
            foreach公司 (无功功率,无功功率  在里面 参数.拆分(" "))
            {
                如果 (!枚举器.移到下一行())
                {
                    枚举器.重置();
                    枚举器.移到下一行();
                }

                地图.添加(新的 字符计数计算作业(), 枚举器.当前);
            }
        }

        返回 地图;
    }

    公众的 计算作业结果策略 OnResult(结果)(IComputeJobResult(计算作业结果)<整数> 物件, IL列表<IComputeJobResult(计算作业结果)<整数>> 反应堆控制系统)
    {
        //如果没有异常,请等待所有作业结果。
        返回 物件.例外 != 无效的 ? 计算作业结果策略.故障转移 : 计算作业结果策略.等待;
    }

    公众的 整数 减少(IL列表<IComputeJobResult(计算作业结果)<整数>> 结果)
    {
        返回 结果.选择(物件 => 物件.数据).总和();
    }
}

公众的 静止的 空隙 MapReduceComputeJob演示()
{
    无功功率,无功功率 点燃 = 点火.起点(新的 点火配置
    {
        发现Spi = 新的 Tcp发现Spi
        {
            本地端口 = 48500,
            本地端口范围 = 20,
            IpFinder(IpFinder) = 新的 TcpDiscoveryStaticIpFinder
            {
                端点 = 新的[]
                {
                    "127.0.0.1:48500..48520"
                }
            }
        }
    });

    无功功率,无功功率 计算 = 点燃.获取计算();

    无功功率,无功功率 物件 = 计算.执行(新的 字符计数任务(), “Hello Grid请计算这些单词中的字符数”);

    慰问.WriteLine(写入行)(“res=” + 物件);
}
此API目前不适用于C++。

通过使用群集组.

处理作业失败

如果某个节点在任务执行过程中崩溃或变得不可用,则为该节点安排的所有作业都会自动发送到另一个可用节点(由于内置的故障切换机制)。但是,如果作业引发异常,则可以将该作业视为失败,并将其故障转移到另一个节点以重新执行。为此,请返回故障切换在中结果(…)方法:

@覆盖
公众的 计算作业结果策略 结果(计算作业结果 物件, 列表<计算作业结果> 反应堆控制系统) {
    点火异常 错误 = 物件.获取异常();

    如果 (错误 != 无效的)
        返回 计算作业结果策略.故障切换;

    //如果没有异常,请等待所有作业结果。
    返回 计算作业结果策略.等待;
}

计算任务适配器

有几个helper类提供了最常用的结果(…)地图(…)方法。

  • 计算机任务适配器-此类实现结果()方法返回故障切换策略,如果作业抛出异常并且等待否则。这意味着此实现将等待所有作业完成并返回结果。

  • ComputeTaskSplitAdapter(计算任务拆分适配器)-这个类扩展了ComputeTaskAdapter(计算任务适配器)并实现地图(…)方法自动将作业分配给节点。它引入了一个新的拆分(…)方法,该方法实现基于输入数据生成作业的逻辑。

分布式任务会话

注释
在中不可用。NET/C#/C++。

对于每个任务,Ignite都会创建一个分布式会话,该会话包含有关任务的信息,并且对任务本身和由此产生的所有作业都可见。您可以使用此会话在作业之间共享属性。属性可以在作业执行之前或期间分配,并以设置顺序对其他作业可见。

@ComputeTaskSessionFull支持
私有的 静止的  任务会话属性任务 延伸 ComputeTaskSplitAdapter(计算任务拆分适配器)<对象, 对象> {

    @覆盖
    受保护的 收藏<? 延伸 计算作业> 分裂(整数 网格大小, 对象 参数) {
        收藏<计算作业> 工作 = 新的 链表<>();

        //按网格中的节点数生成作业。
        对于 (整数  = 0;  < 网格大小; ++) {
            工作.添加(新的 ComputeJobAdapter(计算机作业适配器)(参数) {
                //自动插入的任务会话。
                @任务会话资源
                私有的 计算任务会话 空间站;

                //自动插入的作业上下文。
                @作业上下文资源
                私有的 计算作业上下文 作业Ctx;

                @覆盖
                公众的 对象 执行() {
                    //执行步骤1。
                    // ...

                    //告诉其他工作步骤1已完成。
                    空间站.setAttribute(设置属性)(作业Ctx.获取作业ID(), “第1步”);

                    //等待其他作业完成步骤1。
                    对于 (计算作业同级 兄弟姐妹 : 空间站.获取工作兄弟())
                        尝试 {
                            空间站.等待属性(兄弟姐妹.获取作业ID(), “第1步”, 0);
                        } 抓住 (中断异常 e(电子)) {
                            e(电子).打印堆栈跟踪();
                        }

                    //继续执行步骤2。
                    // ...

                    返回 ...

                }
            });
        }
        返回 工作;
    }

    @覆盖
    公众的 对象 减少(列表<计算作业结果> 结果) {
        //无。
        返回 无效的;
    }

}
此API目前不适用于C#/。净利润。
此API目前不适用于C++。

计算任务示例

以下示例演示了一个简单的字符计数应用程序,该应用程序将给定的字符串拆分为单词,并计算单个作业中每个单词的长度。作业将分布到所有群集节点。

公众的  计算任务示例 {
    公众的 静止的  字符计数任务 延伸 ComputeTaskSplitAdapter(计算任务拆分适配器)<字符串, 整数> {
        // 1. 将收到的字符串拆分为单词
        // 2. 为每个单词创建子作业
        //3。将作业发送到其他节点进行处理。
        @覆盖
        公众的 列表<计算作业> 分裂(整数 网格大小, 字符串 参数) {
            字符串[]  = 参数.分裂(“”);

            列表<计算作业> 工作 = 新的 数组列表<>(.长度);

            对于 (最终的 字符串 单词 : ) {
                工作.添加(新的 计算作业适配器() {
                    @覆盖
                    公众的 对象 执行() {
                        系统.外面的.打印ln(“>>>打印” + 单词 + “从计算作业打开。”);

                        //返回单词中的字母数。
                        返回 单词.长度();
                    }
                });
            }

            返回 工作;
        }

        @覆盖
        公众的 整数 减少(列表<计算作业结果> 结果) {
            整数 总和 = 0;

            对于 (计算作业结果 物件 : 结果)
                总和 += 物件.<整数>获取数据();

            返回 总和;
        }
    }

    公众的 静止的 空隙 主要的(字符串[] 参数) {

        点燃 点燃 = 点火.开始();

        点火计算 计算 = 点燃.计算();

        //在集群上执行任务并等待其完成。
        整数 碳纳米管 = 计算.执行(字符计数任务., “Hello Grid Enabled World!”);

        系统.外面的.打印ln(“>>>短语中的总字符数为“” + 碳纳米管 + "'.");
    }
}
 字符计数计算作业 : ICompute作业<整数>
{
    私有的 只读的 一串 _参数;

    公众的 字符计数计算作业(一串 参数)
    {
        慰问.WriteLine(写入行)(“>>>打印'” + 参数 + “”来自计算作业。“);
        ._参数 = 参数;
    }

    公众的 整数 执行()
    {
        返回 _参数.长度;
    }

    公众的 空隙 取消()
    {
         新的 系统.未实现异常();
    }
}

公众的  计算任务示例
{
    私有的  字符计数任务 : ComputeTaskSplitAdapter(计算任务拆分适配器)<一串, 整数, 整数>
    {
        公众的 覆盖 整数 减少(IL列表<IComputeJobResult(计算作业结果)<整数>> 结果)
        {
            返回 结果.选择(物件 => 物件.数据).总和();
        }

        受保护的 覆盖 I收集<ICompute作业<整数>> 拆分(整数 网格大小, 一串 参数)
        {
            返回 参数.拆分(" ")
                .选择(单词 => 新的 字符计数计算作业(单词))
                .铸造<ICompute作业<整数>>()
                .ToList(待办事项列表)();
        }
    }

    公众的 静止的 空隙 运行ComputeTaskExample()
    {
        无功功率,无功功率 点燃 = 点火.起点(新的 点火配置
        {
            发现Spi = 新的 Tcp发现Spi
            {
                本地端口 = 48500,
                本地端口范围 = 20,
                IpFinder(IpFinder) = 新的 TcpDiscoveryStaticIpFinder
                {
                    端点 = 新的[]
                    {
                        "127.0.0.1:48500..48520"
                    }
                }
            }
        });

        无功功率,无功功率 碳纳米管 = 点燃.获取计算().执行(新的 字符计数任务(), “Hello Grid Enabled World!”);
        慰问.WriteLine(写入行)(“>>>短语中的总字符数为“” + 碳纳米管 + "'.");
    }
}
此API目前不适用于C++。