FLINK cache distribuído e o acumulador

distribuído cache

Flink fornece um cache distribuído, Hadoop semelhante, o usuário pode facilmente ler função no arquivo local paralelo, e colocá-lo nó taskmanager, para evitar a tarefa de puxar repetido. Este mecanismo de cache é a seguinte: para registrar um arquivo ou diretório (sistemas de arquivos locais ou remotos, tais como hdfs ou S3), arquivos de cache e registrado pelo ExecutionEnvironment-se um nome para ele.

Quando o programa é executado, Flink automaticamente copiar arquivos ou diretórios para o sistema de arquivos local taskmanager todos os nós só será executada uma vez. Os usuários podem encontrar o arquivo ou diretório especificado pelo nome e, em seguida, acessá-lo a partir do nó taskmanager sistema de arquivos local.

Na verdade, o cache distribuído é equivalente a transmitir a centelha, para uma transmissão variável para todo o executor, ele também pode ser visto no fluxo de transmissão Flink, mas aqui é um arquivo de transmissão.

Exemplos

Passo 1: Registrar um arquivo, o arquivo pode ser usado em hdfs também podem ser arquivos locais para testes

Passo 2: Use Arquivo

Nota:

Acesse o arquivo de cache ou diretório na função de usuário (aqui é uma função de mapa). Esta função deve herdar RichFunction, porque requer o uso RuntimeContext para ler os dados:

Distribuído código java Cache é a seguinte:

/**
 * <p/> DataSet 分布式缓存 </li>
 * <li>@author: li.pan</li>
 * <li>Date: 2019/12/29 16:10 下午</li>
 * <li>Version: V1.0</li>
 * <li>Description: </li>
 */
public class JavaDataSetDistributedCacheApp {
​
    public static void main(String[] args) throws Exception {
​
        ExecutionEnvironment env =  ExecutionEnvironment.getExecutionEnvironment();
        String filePath = "file:///Users/lipan/workspace/flink_demo/flink-local-train/src/main/resources/sink/java/cache.txt";
​
        // step1: 注册一个本地/HDFS文件
        env.registerCachedFile(filePath, "lp-java-dc");
​
        DataSource<String> data = env.fromElements("hadoop","spark","flink","pyspark","storm");
​
        data.map(new RichMapFunction<String, String>() {
​
            List<String> list = new ArrayList<String>();
            // step2:在open方法中获取到分布式缓存的内容即可
            @Override
            public void open(Configuration parameters) throws Exception {
                File file = getRuntimeContext().getDistributedCache().getFile("lp-java-dc");
                List<String> lines = FileUtils.readLines(file);
                for(String line : lines) {
                    list.add(line);
                    System.out.println("line = [" + line + "]");
                }
            }
​
            @Override
            public String map(String value) throws Exception {
                return value;
            }
        }).print();
​
    }
}
​

Distribuído código scala Cache é a seguinte:

/**
  * <p/>
  * <li>title: DataSet 分布式缓存</li>
  * <li>@author: li.pan</li>
  * <li>Date: 2019/11/23 2:15 下午</li>
  * <li>Version: V1.0</li>
  * <li>Description:
  * step1: 注册一个本地/HDFS文件
  * step2:在open方法中获取到分布式缓存的内容即可
  * </li>
  */

object DistributedCacheApp {

  def main(args: Array[String]): Unit = {

    val env = ExecutionEnvironment.getExecutionEnvironment

    val filePath = "file:///Users/lipan/workspace/flink_demo/flink-local-train/src/main/resources/sink/scala/cache.txt"

    // step1: 注册一个本地/HDFS文件
    env.registerCachedFile(filePath, "pk-scala-dc")

    import org.apache.flink.api.scala._
    val data = env.fromElements("hadoop", "spark", "flink", "pyspark", "storm")
    
    data.map(new RichMapFunction[String, String] {

      // step2:在open方法中获取到分布式缓存的内容即可
      override def open(parameters: Configuration): Unit = {
        val dcFile = getRuntimeContext.getDistributedCache().getFile("pk-scala-dc")

        val lines = FileUtils.readLines(dcFile) // java
        
        /**
          * 此时会出现一个异常:java集合和scala集合不兼容的问题
          */
        import scala.collection.JavaConverters._
        for (ele <- lines.asScala) { 
          println(ele)
        }
      }

      override def map(value: String): String = value
    }).print()
  }

}

Acumulador (acumuladores)

Acumuladores (acumulador) é muito simples, o resultado acumulação final em uma operação de adição, o resultado final pode ser adquirida na execução do trabalho.

O mais simples é o contador de acumulador (contador): Pode ser incrementado por Accumulator.add (valor V), este método. Mesclando todos os resultados no final da tarefa, flink, então, enviar os resultados finais para o cliente. Acumulador na depuração ou se você quiser entender rapidamente quando os seus dados é muito útil.

Há built-bit acumulador Flink, cada um acumulador de ter alcançado interface do acumulador. IntCounter, LongCounter e DoubleCounter: O que se segue é um exemplo de um contador utilizado. Por exemplo: distribuído programa de contagem de palavras.

exemplo:

Passo 1: Criar uma transformação personalizada onde você quer usar operadores para criar objetos em um operador acumulador.

val counter = new LongCounter()

Passo 2: o acumulador registar o objecto, que é geralmente uma função do método aberto rico. Aqui você também pode definir um nome

 getRuntimeContext.addAccumulator("ele-counts-scala", counter)

Passo 3: Utilizar este acumulador operação

counter.add(1)

Passo 4: O resultado final global irá ser armazenada no objecto devolvido a partir JobExecutionResult executar () na. (Esta operação tem de aguardar a conclusão da execução da tarefa)

val num = jobResult.getAccumulatorResult[Long]("ele-counts-scala")

código acumulador Java é a seguinte:

/**
 * <p/>
 * <li>title: flink 计数器</li>
 * <li>@author: li.pan</li>
 * <li>Date: 2019/12/29 2:59 下午</li>
 * <li>Version: V1.0</li>
 * <li>Description:
 * Java实现通过一个add操作累加最终的结果,在job执行后可以获取最终结果
 * </li>
 */
public class JavaCounterApp {

    public static void main(String[] args) throws Exception {

        ExecutionEnvironment env = ExecutionEnvironment.getExecutionEnvironment();
        DataSource<String> data = env.fromElements("hadoop","spark","flink","pyspark","storm");

        DataSet<String> info = data.map(new RichMapFunction<String, String>() {

            LongCounter counter = new LongCounter();

            @Override
            public void open(Configuration parameters) throws Exception {
                super.open(parameters);

                getRuntimeContext().addAccumulator("ele-counts-java", counter);
            }

            @Override
            public String map(String value) throws Exception {
                counter.add(1);
                return value;
            }
        });

        String filePath = "file:///Users/lipan/workspace/flink_demo/flink-local-train/src/main/resources/sink/java/";
        info.writeAsText(filePath, FileSystem.WriteMode.OVERWRITE).setParallelism(2);
        JobExecutionResult jobResult = env.execute("CounterApp");

        // step3: 获取计数器
        long num = jobResult.getAccumulatorResult("ele-counts-java");

        System.out.println("num = [" + num + "]");
    }
}

código acumulador Scala é a seguinte:

/**
  * <p/>

  * <li>Description: flink 计数器</li>
  * <li>@author: panli@[email protected]</li>

  * <li>Date: 2019-04-14 21:53</li>

  * Scala实现通过一个add操作累加最终的结果,在job执行后可以获取最终结果
  */
object CountApp {

  def main(args: Array[String]): Unit = {

    val env = ExecutionEnvironment.getExecutionEnvironment
    val data = env.fromElements("hadoop", "spark", "flink", "pyspark", "storm")


    val info = data.map(new RichMapFunction[String, String]() {
      // step1:定义计数器
      val counter = new LongCounter()

      override def open(parameters: Configuration): Unit = {
        // step2: 注册计数器
        getRuntimeContext.addAccumulator("ele-counts-scala", counter)
      }

      override def map(in: String): String = {
        counter.add(1)
        in
      }
    })

    val filePath = "file:///Users/lipan/workspace/flink_demo/flink-local-train/src/main/resources/sink/scala/"
    info.writeAsText(filePath, WriteMode.OVERWRITE).setParallelism(2)
    val jobResult = env.execute("CounterApp")

    // step3: 获取计数器
    val num = jobResult.getAccumulatorResult[Long]("ele-counts-scala")

    println("num: " + num)
  }

}

 

Publicado 87 artigos originais · Louvor obteve 69 · vista 130 000 +

Acho que você gosta

Origin blog.csdn.net/lp284558195/article/details/103764646
Recomendado
Clasificación