Árvore Binária de Busca Ótima - Uma Implementação Distribuída

Documentos relacionados
DESENVOLVIMENTO DE UM ALGORITMO PARALELO PARA APLICAÇÃO EM CLUSTER DE COMPUTADORES

COMPUTAÇÃO PARALELA E DISTRIBUÍDA

Cálculo da árvore binária de busca ótima usando MPI

Programação Concorrente e Paralela: Algoritmo paralelo para o Crivo de Eratóstenes

Aluno de Pós-Graduação em Engenharia de Software para Dispositivos Móveis pela UNINTER

Aluno do Curso de Ciência da Computação UNIJUÍ, 3

Programação de Alto Desempenho - 2. Prof: Carla Osthoff

BALANCEAMENTO DE CARGA EM SISTEMAS MULTIPROCESSADORES UTILIZANDO O MODELO DE PROGRAMAÇÃO CHARM++ 1

CRIVO QUADRÁTICO: IMPLEMENTAÇÃO DA OBTENÇÃO DE UM CONJUNTO DE NÚMEROS COMPLETAMENTE FATORADOS SOBRE UMA BASE DE FATORES

ANÁLISE DE DESEMPENHO COM A PARALELIZAÇÃO DO CÁLCULO DE NÚMEROS PERFEITOS 1

Técnicas de Processamento Paralelo na Geração do Fractal de Mandelbrot

Informática I. Aula 14. Aula 14-10/10/2007 1

Introdução OpenMP. Nielsen Castelo Damasceno

AVALIAÇÃO DE DESEMPENHO DE PROCESSAMENTO DISTRIBUÍDO EM LARGA ESCALA COM HADOOP

Introdução aos Conceitos de Computação Paralela através da estimativa de Pi

Sistemas Operacionais II. Prof. Gleison Batista de Sousa Aula 01

Paralelização de Algoritmos de CFD em Clusters Multi-Core MC7. Escola de Verão Arquiteturas Multi-Core

COMPARAÇÃO DE DESEMPENHO ENTRE IMPLEMENTAÇÕES DO ALGORITMO JOGO DA VIDA COM PTHREAD E OPEMMP 1

Monografia de Conclusão do Curso de Graduação em Ciência da Computação. 2

Sistemas Operacionais II. Prof. Gleison Batista de Sousa Aula 01

O Que Veremos. Introdução. Introdução. Definindo Desempenho. Definindo Desempenho. Avaliando e Compreendendo o Desempenho

Computadores podem ser úteis em problemas que envolvem: Grande número de dados. Grande número de cálculos. Complexidade. Precisão.

Apresentação dos Serviços para Processamento de Dados de Alto Desempenho disponibilizados pela InterNuvem

Universidade Estadual de Mato Grosso do Sul UEMS Curso de Ciência da Computação Disciplina de Algoritmos Paralelos e Distribuídos

Avaliação de desempenho

Paradigmas de Processamento Paralelo na Resolução do Fractal de Mandelbrot

DGPAPP Tutorial. Introdução. Daniel Centeno Einloft Vinicius Meirelles Pereira. 20 May 2014

Medida de desempenho

Algoritmos Paralelos usando CGM/MPI. Edson Norberto Cáceres e Siang Wun Song DCT/UFMS e DCC/IME/USP Aula 05

Programação dinâmica

Um Calculador de Capacidade de Computação para Nós de Máquinas Virtuais LAM/MPI

A IMPORTÂNCIA DE THREADS NO DESEMPENHO DE APLICAÇÕES

PROJETO E ANÁLISE DE ALGORITMOS (INF 2926)

Análise de Desempenho da Paralelização do Problema de Caixeiro Viajante

BOINC + R: Executando rotinas de

Toward an Architecture-Independent Analysis of Parallel Algorithms

Sistema Distribuído. Sistema Distribuído. Aplicações Distribuídas. Conceitos Básicos

Supercomputador Pleiades

Branch-and-Bound para problemas de Otimização Combinatória

Implementação e Desenvolvimentos de Grade Computacional

1 Como compilar seu código? 2 Comandos de terminal:

UM ESTUDO COMPARATIVO DE DESEMPENHO UTILIZANDO PROGRAMAÇÃO SEQUENCIAL VS PARALELA APLICADO EM ALGORITMOS GENÉTICOS 1

Desempenho. Sistemas de Computação

Linguagens de Programação

PCC104 Projeto e Análise de Algoritmos

Sistemas Operacionais I

Arquitecturas Paralelas I Computação Paralela em Larga Escala LESI - 4º Ano. Desenvolvimento de Aplicações Paralelas

AULA 15. Algoritmos p.600/637

Trabalho de Análise de Algoritmos. Problema da Mochila

OpenWrt: modelagem do

OpenMP: Variáveis de Ambiente

Bruno da Silva de Oliveira. Hydra: Compilação Distribuída de código fonte

Aplicação de Processamento Paralelo com GPU a Problemas de Escoamento Monofásico em Meios Porosos. Bruno Pereira dos Santos Dany Sanchez Dominguez

PARALELIZAÇÃO DE ALGORITMO DE INSPEÇÃO DE ROTAS UTILIZANDO PERMUTAÇÃO LEXICOGRÁFICA 1

5.1 Gerenciamento de Memória

Organização de Computadores I

Cluster Computing: Estudo de Caso no LCCV/CTEC

AULA 06: PROGRAMAÇÃO EM MÁQUINAS PARALELAS

Introdução ao Python. Programa Computacional

Um Mecanismo de Auto Elasticidade com base no Tempo de Resposta para Ambientes de Computação em Nuvem baseados em Containers

Organização de Computadores e Proj.Integrado. Desempenho Herbert Rausch Fernandes

Avaliação de desempenho e dependabilidade de processamento de dados em larga escala com Hadoop

Alguns Aspectos de Desempenho e Utilização de Aglomerados de Computadores Heterogêneos 1

TÍTULO: PROGRAMAÇÃO PARALELA - UMA INTRODUÇÃO AO PARALELISMO COM A OPENMPI

Computação Paralela e Distribuída. Heucles Jr

Sistemas Distribuídos

for(int x=0; x < width; x++) { for(int y=0; y < height; y++) { finalimage[x][y]=renderpixel(x,y, &scenedata); } }

Alocação de processos a processadores. equilíbrio de carga e oportunismo

CI218 - Trabalho - 2 o sem/2016

Benchmarks. 1. Introdução

Processamento Paralelo

Arquitetura de Computadores Aula 11 - Multiprocessamento

Introdução à Ciência da Computação II

Sistemas de Informação. Sistemas Operacionais

1.1 Descrição do problema A programação genética (PG) é uma meta-heurística utilizada para gerar programas de computadores, de modo que o computador

Resolução de Problemas com Computador. Resolução de Problemas com Computador. Resolução de Problemas com Computador

Avaliação do Tempo de Processamento e Comunicação via Rotinas MPI Assíncronas no Modelo OLAM

FACULDADE DE TECNOLOGIA SENAC PELOTAS. Trabalho de Shellscript Atividade 5 Introdução a Informática

Informática Aplicada. Introdução

Programação Concorrente e Paralela

Arquiteturas Paralelas

ORGANIZAÇÃO E ARQUITETURA DE COMPUTADORES II AULA 04: PROCESSAMENTO PARALELO: MULTICOMPUTADOR

DEPARTAMENTO DE CIÊNCIA DA COMPUTAÇÃO BACHARELADO EM INFORMÁTICA SISTEMAS OPERACIONAIS I 1 0 SEM/05 Teste 1 Unidade I DURAÇÃO: 50 MINUTOS

Predição de Utilização de Recursos Computacionais Usando Séries Temporais

IDES E PROGRAMAÇÃO. Prof. Dr. Cláudio Fabiano Motta Toledo PAE: Maurício A Dias

Grupo de Usuários Java do Noroeste Paulista. Introdução à tecnologia Java

Tópicos: Computação de Alto Desempenho no Cluster Oscar - Passo a passo

Manual de Instalação APS AUDATEXWEB

Algoritmos Computacionais

O Pronome ALL 7.1. O Conjunto de Todos os Objetos do Sistema

BCC201 Introdução à Programação. Prof. Saul Delabrida 2013/2

Paralelização Eficiente para o Algoritmo Binário de Exponenciação Modular

Algoritmos e Técnicas de Programação. Professora Luciana Faria

Intel Thread Building Blocks (TBB)

Organização de Sistemas Computacionais Processadores: Organização da CPU

INFORMÁTICA. 03. O Internet Relay Chat permite que diversas pessoas realizem comunicação on-line por meio da Internet.

The future is parallel but it may not be easy

Nem todos os problemas algorítmicos que podem ser resolvidos em princípio podem ser resolvidos na prática: os recursos computacionais requeridos

Objetivos. Responder o que é Java; Mostrar as vantagens e desvantagens do Java; Compilar e executar um programa simples.

Transcrição:

Árvore Binária de Busca Ótima - Uma Implementação Distribuída Felipe Reis e Caio Valentim Departamento de Informática PUC-Rio 7 de novembro de 2010 1 Introdução O problema de encontrar a árvore binária de busca ótima para um conjunto de frequências é estudado há anos no meio acadêmico. O melhor algoritmo exato conhecido é uma programação dinâmica de complexidade O(n 2 ) [3]. Contudo, o algoritmo sequencial não é facilmente paralelizável. Existem algumas propostas, como em [2] e [1]. Mas, em geral, o apresentado não é uma solução exata ou é complicado demais. Neste documento apresentamos nosso desenvolvimento e implementação de uma versão distribuída simples para o problema. 2 Definição do Problema O problema em questão é o de encontrar uma árvore binária de busca ótima para um conjunto de chaves dadas as frequências de cada chave. Formalmente, temos as chaves A = {a 1 a 2... a n }, as frequências de buscas com sucesso de cada chave F = {f 1, f 2,..., f n } e as frequências de buscas sem sucesso Q = {q 0, q 1,..., q n, q n+1 }. Onde q i representa a frequência de buscas por chaves entre a i e a i+1. Nesse trabalho iremos assumir que todas as buscas são com sucesso. Ou seja, iremos descartar o conjunto Q. Desta forma, queremos criar uma árvore binária de busca que minimize a seguinte função: onde n(i) é o nível do nó i na árvore. n f i n(i) i=1 1

3 Artigos Relacionados Os dois principais artigos estudados foram [2] e [1]. No primeiro, M. Karpinski propõe uma solução paralela capaz de calcular a solução ótima em tempo O(n 1 ɛ ) para uma constante arbitrária 0 < ɛ 1/2. Ele agrupa as diagonais em conjuntos e calcula cada conjunto de forma eficiente a partir do pré-processamento de uma estrutura que ele chama sub-árvores especiais. Apesar de interessante, a arbodagem não é fácil de implementar, especialmente para quem não possui grande experiência com codificação em paralelo. Em outra linha, C. Mitica propõe em [1] uma solução paralela que começa dividindo o conjunto de chaves em intervalos menores, calculando as árvores ótimas para cada intervalo menor e, a partir das árvores de cada sub-intervalo, constroi uma solução para todo conjunto. Essa solução não foi implementada pois acreditamos que a abordagem está errada e, de fato, não produz uma árvore ótima. 4 Solução Sequencial Abaixo dois lemas úteis para construção do algoritmo sequencial. Lemma 4.1 (Critério de Otimalidade). Seja OP T (i, j) o custo da árvore ótima para as chaves {a i,..., a j 1 }. A seguinte recorrência vale: j 1 OP T (i, j) = min {OP T (i, k) + OP T (k + 1, j)} + i k<j Lemma 4.2 (Princípio da Monoticidade). Seja r a chave que será a raiz da árvore ótima do intervalo [i, j) e [i, j ) outro intervalo tal que i i j j com raiz ótima r. Vale que r r. Com o primeiro resultado é fácil construir uma tabela com a solução ótima em tempo O(n 3 ), usando o segundo lema podemos reduzir a complexidade para O(n 2 ). Contudo, nossa versão distribuída se basea na construção O(n 3 ) implementada no capítulo 8 do livro [4]. 5 Algoritmo Distribuído O algoritmo, derivado do segundo lema, na prática, consiste em preencher diagonal por diagonal de uma tabela de dimensões n n. Desta forma, como o tempo para calcular cada diagonal é proporcional a O(n 2 ), decidimos paralelizar esse cálculo. Existem n diagonais então, de forma geral, nosso algoritmos consiste em: for i = 0 to n do 1. Cada processo calcula um pedaço da i-ésima diagonal 2. Cada processo distribui o seu pedaço entre os outros processos done 2 t=i f t

Ou seja, cada processo fica resposável por um pedaço da diagonal que está sendo calculada no momento. Após o cálculo, os processos têm que comunicar sua parcela aos outros processos. O procedimento se repete até que não existam mais diagonais para calcular. Com isso, o tempo esperado para o cálculo de cada diagonal é proporcional a O(n 2 /p+np). A primeira parcela da soma se refere ao processamento paralelo da diagonal e a segunda ao custo extra de comunicação. 6 Implementação 6.1 Detalhes do Cluster O programa foi rodado no cluster da PUC-Rio que conta com 64 nós. Abaixo temos uma descrição técnica do cluster retirada do site do suporte do departamento. A versão do MPI usada foi LAM 7.0.6/MPI 2 C++. O site da PUC é formado atualmente por três clusters: o primeiro, com 12 estações; o segundo, com 20 estações; e o terceiro, com 32 estações. Todos estão situados fisicamente no server farm do DI. A arquitetura de cada cluster é homogênea: os nós do primeiro cluster têm CPUs Intel Core 2 Duo 2.16 GHz e 1 GB de RAM; os do segundo têm CPUs Intel Pentium IV 1.70 GHz e 256 Mb de RAM; e os do terceiro têm CPUs Intel Pentium II 400 MHz (Deschutes) e 280 Mb de RAM. Os sistemas operacionais instalados são: no primero cluster, Fedora Core 8 kernel 2.6.25.4-10; e, nos demais, Red Hat Linux vers~ao 9 kernel 2.4.20-31.9. A versão de globus é 2.4 em todos os clusters. As versões de MPI disponíveis são lam-7.1.2, lam-7.0.6 e mpich-1.2.6. O domínio do cluster é par.inf.puc-rio.br. Os nós estão numerados do n00 até o n63. O ponto de acesso (via SSH) é a máquina server.par.inf.puc-rio.br. A partir dela, os nós podem ser acessados via RSH ou SSH. As conexões entre os nós e o switch são de 100Mbs. Cada usuário possui uma área própria de trabalho em cada nó, localizada no /home/local/login_usuár e acesso remoto a sua área de trabalho na máquina server.par.inf.puc-rio.br, através da pasta /home/server/login_usuario. 6.2 Executando Código MPI Uma vez que usamos a implementação LAM do MPI disponível no cluster, alguns passos foram necessários para conseguir efetivamente executar nosso código. Em primeiro lugar, antes de rodar o programa, deve-se criar uma associação entre um conjunto de máquinas (LAM). Isso é feito com o camando lamboot -v machines.txt. O flag -v é de verbose e o arquivo machines.txt contém as máquinas que serão utilizadas. Para o comando funcionar, uma série de requisitos devem ser observados. Por exemplo, as máquinas devem permitir acesso ssh sem senha. Para verificar se o ambiente está corretamente configurado, podemos usar o camando recon -v que lista possíveis problemas. Além do ambiente de execução, precisamos de um código compilado. Para compilar utilizamos o mpicc, compilador C++ para código MPI. Com o código compilado, o próximo passo é distribuir o executável entre as máquinas do cluster. O suporte do DI disponibiliza o script mrcp para realizar esta tarefa. 3

Por fim, com todos os passos anteriores feitos, podemos executar, por exemplo, mpirun -np 8 a.out, que roda o programa a.out de forma distribuída entre 8 processos. 7 Experimentos Os experimentos foram executados com 1, 4 e 8 processos rodando em máquinas separadas. Testamos com entradas de tamanho 10, 50, 100, 500, 1000 e 5000. O tempo de execução para cada par entrada x números de processos é a média de 10 execuções. Abaixo a tabela dos resultados obtidos: p 10 50 100 500 1000 3000 5000 1 0.521 0.522 0.520 0.850 3.344 107.159 503.236 4 0.555 0.571 0.580 0.910 2.569 63.275 295.765 8 0.58 0.610 0.650 1.061 2.379 38.024 172.599 E os resultados acima estão dispostos também na figura 1. 4

600 500 Tempo x Tamanho entrada 1 processo 4 processos 8 processos + + 400 300 200 100 + 0 + + + 0 500 1000 1500 2000 2500 3000 3500 4000 4500 5000 Numero de chaves 8 Conclusão Figura 1: Tempos de Execução De acordo com os experimentos realizados, é possível notar uma melhora significativa no tempo de execução total para entradas superiores a 1000 chaves, como esperávamos alcançar utilizando computação distribuída. Analisando o teste de 5000 chaves, por exemplo, temos um ganho de tempo de 291, 5%, no comparativo entre a execução sequencial e a execução distribuída em 8 processos. Outro resultado que também é possível identificar através dos experimentos realizados, é o ônus introduzido pela comunicação entre processo, necessária para mantê-los sincronizados, na versão distribuída do algoritmo. Se observarmos a execução do algoritmo para um conjunto de 500 chaves, por exemplo, percebemos que a execução entre 8 processos é cerca de 11% mais custosa do que a execução para 4 processos, e 20% mais ineficiente do que a versão paralela. Em suma, o algoritmo distribuído, para o problema de encontrar a árvore de binária de busca ótima, apresentou-se bem mais eficiente, se comparado a sua versão sequencial para um conjunto grande de chaves. No entanto, executando-o com poucas chaves, sua utilização não compensa o tempo gasto com comunicação e sincronização entre processos. Referências [1] Mitica Craus. Parallel and distributed solutions for the optimal binary search tree problem. In IWCC 01: Proceedings of the NATO Advanced Research Workshop on Advanced Environments, Tools, and Applications for Cluster Computing-Revised Papers, pages 103 117, London, UK, 2002. Springer-Verlag. 5

[2] Marek Karpinski and Wojciech Rytter. On a sublinear time parallel construction of optimal binary search trees, 1994. [3] Donald E. Knuth. Optimum binary search trees. Acta Inf., 1:14 25, 1971. [4] Michael Quinn. Parallel Programming in C with MPI and OpenMP. Elizabeth A. Jones, 2004. 6