diff options
author | Dmitrii Kuznetsov <torgeek@users.noreply.github.com> | 2021-02-22 18:36:35 +0300 |
---|---|---|
committer | GitHub <noreply@github.com> | 2021-02-22 18:36:35 +0300 |
commit | bc8bd2646f068cfb402850f7c0f9b1dbfe81e5a0 (patch) | |
tree | 89213fd6afbf9cc9303c1c2fa08dafc840a9d99d /pt-br | |
parent | 363d5281f1e3d5bee6339b5316405b0a4b592c49 (diff) | |
parent | 110511a10110f96b20f107c078f7d5ef4c01b109 (diff) |
Merge pull request #1 from adambard/master
Merge from original adambard
Diffstat (limited to 'pt-br')
64 files changed, 9701 insertions, 1844 deletions
diff --git a/pt-br/amd.html.markdown b/pt-br/amd-pt.html.markdown index 38c1f70f..40c7cd09 100644 --- a/pt-br/amd.html.markdown +++ b/pt-br/amd-pt.html.markdown @@ -141,7 +141,7 @@ require(['jquery', 'coolLibFromBower', 'modules/algunsHelpers'], function($, coo coolLib.facaAlgoDoidoCom(helpers.transform($('#foo'))); }); ``` -Apps baseados em `require.js` geralmente terão u´m único ponto de acesso (`main.js`) que é passado à tag script do `require.js` como um data-attribute. Ele vai ser automaticamente carregado e executado com o carregamento da página: +Apps baseados em `require.js` geralmente terão um único ponto de acesso (`main.js`) que é passado à tag script do `require.js` como um data-attribute. Ele vai ser automaticamente carregado e executado com o carregamento da página: ```html <!DOCTYPE html> diff --git a/pt-br/asciidoc-pt.html.markdown b/pt-br/asciidoc-pt.html.markdown index 75b3c268..b12c0693 100644 --- a/pt-br/asciidoc-pt.html.markdown +++ b/pt-br/asciidoc-pt.html.markdown @@ -87,10 +87,6 @@ Título de seções ===== Nível 4 <h5> -====== Nível 5 <h6> - -======= Nível 6 <h7> - ``` Listas @@ -103,7 +99,7 @@ Para criar uma lista com marcadores use asteriscos. * baz ``` -Para criar uma lista númerada use pontos. +Para criar uma lista numerada use pontos. ``` . item 1 diff --git a/pt-br/asymptotic-notation-pt.html.markdown b/pt-br/asymptotic-notation-pt.html.markdown index 2e299d09..b70d26b7 100644 --- a/pt-br/asymptotic-notation-pt.html.markdown +++ b/pt-br/asymptotic-notation-pt.html.markdown @@ -13,7 +13,7 @@ lang: pt-br ## O que é? Notação Assintótica é uma linguagem que nos permite analisar o tempo de execução - de um algoritmo através da indentificação de seu comportamento com o + de um algoritmo através da identificação de seu comportamento com o crescimento da entrada oferecida. Isso também é conhecido como taxa de crescimento do algoritmo. O algoritmo de repente torna-se lento quando o tamanho da entrada cresce? O algoritmo mantém, em geral, seu tempo de execução @@ -33,12 +33,12 @@ Um modo seria contar o número de operações primitivas com diferentes tamanhos ## Tipos de Notação Assintótica -Na primeira seção desse documento, descrevemos como Notação Assintótica identifica o comportamento de um algoritmo +Na primeira seção deste documento, descrevemos como Notação Assintótica identifica o comportamento de um algoritmo a medida que o tamanho da entrada cresce. Imaginemos um algoritmo como uma função *f*, *n* como o tamanho da entrada e *f(n)* sendo o tempo de execução. Então, para dado algoritmo *f*, com entrada de tamanho *n*, você terá tempo de execução - *f(n)*. Isto resulta em um gráfico onde a coordernada Y é o tempo de execução -, a coordernada X representa o tamanho da entrada e os pontos representao o tempo + *f(n)*. Isto resulta em um gráfico onde a coordenada Y é o tempo de execução, + a coordenada X representa o tamanho da entrada e os pontos representam o tempo de execução para dado tamanho de entrada. Você pode representar a função, ou o algoritmo, com Notação Assintótica de várias @@ -49,7 +49,7 @@ não avalia o melhor caso, porque essas condições não são atingidas com freq Um bom exemplo disto seria em algoritmos de ordenação; especificamente, na adição de elementos à árvores. O melhor caso na maioria de algoritmos pode ser de apenas uma operação. Entretanto, na maioria dos casos, o elemento a ser adicionado terá -que percorrer a árvore de forma apropriada, o que pode causar a analise de um +que percorrer a árvore de forma apropriada, o que pode causar a análise de um ramo inteiro. Este é o pior caso, e isto é o que você está se preparando. @@ -63,16 +63,16 @@ Função Polinomial - an^z + . . . + an^2 + a*n^1 + a*n^0, onde *z* é uma const Função Exponencial - a^n, onde a é alguma constante ``` Estas são as funções básicas de crescimento usadas em várias notações. A lista - começa com a de crescimento mais lento (logarítima, a de execução mais rápida) + começa com a de crescimento mais lento (logarítmica, a de execução mais rápida) e segue para a de crescimento mais rápido (exponencial, de execução mais lenta). -Repare que enquando *n*, a entrada, cresce, cada uma dessas funções cresce mais -rápido que quadrático, polinimial e exponencial, comparadas com logaritma e linear. +Repare que enquanto *n*, a entrada, cresce, cada uma dessas funções cresce mais +rápido que quadrático, polinomial e exponencial, comparadas com logarítmica e linear. Uma nota extremamente importante para notações é tentar usar os termos mais simples. Isto significa descartar constantes e termos de ordem mais baixa, pois quando o tamanho da entrada cresce para o infinito (limites matemáticos), os termos de ordem mais baixa e constantes tornam-se irrelevantes. Por exemplo, se você tiver uma -constante muito grande, 2^9001, a simplificação não afeterá sua notação. +constante muito grande, 2^9001, a simplificação não afetará sua notação. Já que queremos as formas mais simples, mudemos nossa tabela um pouco... @@ -87,8 +87,8 @@ Função Exponencial - a^n, onde *a* é uma constante ### Big-O Big-O, também escrita como O, é uma Notação Assintótica para o pior caso. Digamos -*f(n)* seja o tempo de exeução de um algoritmo e *g(n)) um tempo de complexidade -arbritário que você quer relacionar com seu algoritmo. *f(n)* é O(g(n)), se, para +*f(n)* seja o tempo de execução de um algoritmo e *g(n)) um tempo de complexidade +arbitrário que você quer relacionar com seu algoritmo. *f(n)* é O(g(n)), se, para quando constante real c (c > 0), *f(n)* <= *c g(n)* para todo tamanho de entrada n (n > 0). @@ -116,7 +116,7 @@ Há alguma constante c que satisfaça a definição para todo n? 3log n + 100 <= 150 * log n, n > 2 (Indefinido em n = 1) ``` -Sim! A definição de Big-I for atentida, portante `f(n)` é `O(g(n))`. +Sim! A definição de Big-O foi atendida, portanto `f(n)` é `O(g(n))`. *Exemplo 2* @@ -146,7 +146,7 @@ Big-Omega, também escrita como Ω, é uma Notação Assintótica para o melhor Sinta-se livre para adicionar mais exemplos. Big-O é a notação primária usada para medir complexidade de algoritmos. ### Notas Finais -É difícil manter esse tipo de tópico curto e você deveria ler os livros e artigos listados abaixo. Eles cobrem muito mais profundamente definições e exemplos. Mais x='Algoritms & Data Structures' virá; teremos um documento sobre analisar código em breve. +É difícil manter esse tipo de tópico curto e você deveria ler os livros e artigos listados abaixo. Eles cobrem muito mais profundamente definições e exemplos. Mais x='Algorithms & Data Structures' virá; teremos um documento sobre analisar código em breve. ## Livros diff --git a/pt-br/asymptoticnotation-pt.html.markdown b/pt-br/asymptoticnotation-pt.html.markdown deleted file mode 100644 index c5299a11..00000000 --- a/pt-br/asymptoticnotation-pt.html.markdown +++ /dev/null @@ -1,161 +0,0 @@ ---- -category: Algorithms & Data Structures -name: Asymptotic Notation -contributors: - - ["Jake Prather", "http://github.com/JakeHP"] -translators: - - ["Carolina Knoll", "http://github.com/carolinaknoll"] -lang: pt-br ---- - -# Aprenda X em Y minutos -## Onde X=Notação Assintótica - -# Notações Assintóticas -## O que são? - -Notações assintóticas são notações matemáticas que nos permitem analisar tempo de execução -de um algoritmo, identificando o seu comportamento de acordo como o tamanho de entrada para -o algoritmo aumenta. Também é conhecido como taxa de "crescimento" de um algoritmo. O algoritmo -simplesmente se torna incrivelmente lento conforme o seu tamanho aumenta? Será que pode-se na -maior parte manter o seu tempo de execução rápido mesmo quando o tamanho de entrada aumenta? -A notação assintótica nos dá a capacidade de responder a essas perguntas. - -## Além desta, existem outras alternativas para responder a essas perguntas? - -Uma forma seria a de contar o número de operações primitivas em diferentes tamanhos de entrada. -Embora esta seja uma solução válida, a quantidade de trabalho necessário, mesmo para algoritmos -simples, não justifica a sua utilização. - -Outra maneira é a de medir fisicamente a quantidade de tempo que leva para se executar um algoritmo -de diferentes tamanhos. No entanto, a precisão e a relatividade (já que tempos obtidos só teriam -relação à máquina em que eles foram testados) deste método estão ligadas a variáveis ambientais, -tais como especificações de hardware, poder de processamento, etc. - -## Tipos de Notação Assintótica - -Na primeira seção deste documento nós descrevemos como uma notação assintótica identifica o comportamento -de um algoritmo como as alterações de tamanho de entrada (input). Imaginemos um algoritmo como uma função -f, n como o tamanho da entrada, e f (n) sendo o tempo de execução. Assim, para um determinado algoritmo f, -com tamanho de entrada n você obtenha algum tempo de execução resultante f (n). Isto resulta num gráfico, -em que o eixo Y representa o tempo de execução, o eixo X é o tamanho da entrada, e os pontos marcados são -os resultantes da quantidade de tempo para um dado tamanho de entrada. - -Pode-se rotular uma função ou algoritmo com uma notação assintótica de diversas maneiras diferentes. -Dentre seus exemplos, está descrever um algoritmo pelo seu melhor caso, pior caso, ou caso equivalente. -O mais comum é o de analisar um algoritmo pelo seu pior caso. Isso porque você normalmente não avaliaria -pelo melhor caso, já que essas condições não são as que você está planejando. Um bom exemplo disto é o de -algoritmos de ordenação; especificamente, a adição de elementos a uma estrutura de tipo árvore. O melhor -caso para a maioria dos algoritmos pode ser tão simples como uma única operação. No entanto, na maioria -dos casos, o elemento que você está adicionando terá de ser ordenado de forma adequada através da árvore, -o que poderia significar a análise de um ramo inteiro. Este é o pior caso, e é por ele que precisamos seguir. - -### Tipos de funções, limites, e simplificação - -``` -Função Logaritmica - log n -Função Linear - an + b -Função Quadrática - an^2 + bn + c -Função Polinomial - an^z + . . . + an^2 + a*n^1 + a*n^0, onde z é uma constante -Função Exponencial - a^n, onde a é uma constante -``` - -Estas são algumas classificações básicas de crescimento de função usados em várias notações. A lista -começa com a função crescimento mais lento (logarítmica, com tempo de execução mais rápido) e vai até -a mais rápida (exponencial, com tempo de execução mais lento). Observe que 'n', ou nossa entrada, -cresce em cada uma dessas funções, e o resultado claramente aumenta muito mais rapidamente em função -quadrática, polinomial e exponencial, em comparação com a logarítmica e a linear. - -Uma observação de boa importância é que, para as notações a serem discutidas, deve-se fazer o melhor -para utilizar termos mais simples. Isto significa desrespeitar constantes, e simplificar termos de -ordem, porque, como o tamanho da entrada (ou n no nosso f (n) exemplo) aumenta infinitamente (limites -matemáticos), os termos em ordens mais baixas e constantes são de pouca ou nenhuma importância. Dito -isto, se você possui constantes com valor 2^9001, ou alguma outra quantidade ridícula, inimaginável, -perceberá que a simplificação distorcerá a precisão de sua notação. - -Já que nós queremos a forma mais simples, vamos modificar nossas funções um pouco. - -``` -Logaritmica - log n -Linear - n -Quadrática - n^2 -Polinomial - n^z, onde z é uma constante -Exponencial - a^n, onde a é uma constante -``` - -### O Grande-O - -Grande-O, geralmente escrita como O, é uma Notação Assintótica para o pior caso para uma dada função. Digamos -que `f(n)` é o tempo de execução de seu algoritmo, e `g(n)` é uma complexidade de tempo arbitrário que você está -tentando se relacionar com o seu algoritmo. `f(n)` será O(g(n)), se, por qualquer constante real c (c > 0), -`f(n)` <= `c g(n)` para cada tamanho de entrada n (n > 0). - -*Exemplo 1* - -``` -f(n) = 3log n + 100 -g(n) = log n -``` - -É `f(n)` um O(g(n))? -É 3 `log n + 100` igual a O(log n)? -Vamos checar na definição de Grande-O. - -``` -3log n + 100 <= c * log n -``` - -Existe alguma constante c que satisfaça isso para todo n? - -``` -3log n + 100 <= 150 * log n, n > 2 (indefinido em n = 1) -``` - -Sim! A definição de Grande-O foi satisfeita. Sendo assim, `f(n)` é O(g(n)). - -*Exemplo 2* - -``` -f(n) = 3 * n^2 -g(n) = n -``` - -É `f(n)` um O(g(n))? -É `3 * n^2` um O(n)? -Vamos ver na definição de Grande-O. - -``` -3 * n^2 <= c * n -``` - -Existe alguma constante que satisfaça isso para todo n? -Não, não existe. `f(n)` NÃO É O(g(n)). - -### Grande-Omega - -Grande-Omega, comumente escrito como Ω, é uma Notação Assintótica para o melhor caso, ou -uma taxa de crescimento padrão para uma determinada função. - -`f(n)` é Ω(g(n)), se, por qualquer constante c real (c > 0), `f(n)` é >= `c g(n)` para cada -tamanho de entrada n (n > 0). - -Sinta-se livre para pesquisar recursos adicionais e obter mais exemplos sobre este assunto! -Grande-O é a notação primária utilizada para tempo de execução de algoritmos, de modo geral. - -### Notas de Finalização - -É complicado exibir este tipo de assunto de forma tão curta, então é definitivamente recomendado -pesquisar além dos livros e recursos on-line listados. Eles serão capazes de analisar o assunto com -uma profundidade muito maior, além de ter definições e exemplos. Mais sobre onde X="Algoritmos e -Estruturas de Dados" está a caminho: Haverá conteúdo focado na análise de exemplos de códigos reais -em breve. - -## Livros - -* [Algorithms] (http://www.amazon.com/Algorithms-4th-Robert-Sedgewick/dp/032157351X) -* [Algorithm Design] (http://www.amazon.com/Algorithm-Design-Foundations-Analysis-Internet/dp/0471383651) - -## Recursos Online - -* [MIT] (http://web.mit.edu/16.070/www/lecture/big_o.pdf) -* [KhanAcademy] (https://www.khanacademy.org/computing/computer-science/algorithms/asymptotic-notation/a/asymptotic-notation) diff --git a/pt-br/awk-pt.html.markdown b/pt-br/awk-pt.html.markdown new file mode 100644 index 00000000..70d0a01c --- /dev/null +++ b/pt-br/awk-pt.html.markdown @@ -0,0 +1,377 @@ +--- +category: tool +tool: awk +filename: learnawk-pt.awk +contributors: + - ["Marshall Mason", "http://github.com/marshallmason"] +translators: + - ["Paulo Henrique Rodrigues Pinheiro", "https://github.com/paulohrpinheiro"] +lang: pt-br + +--- + +AWK é uma ferramenta padrão em todos os sistemas UNIX compatíveis com POSIX. É +como um Perl despojado, perfeito para tarefas de processamento de texto e +outras tarefas de script. Possui uma sintaxe C-like, mas sem ponto e vírgula, +gerenciamento manual de memória, ou tipagem estática. Destaca-se no +processamento de texto. Você pode chamá-lo a partir de um shell-script, ou você +pode usá-lo como uma linguagem de script autônomo. + +Por que usar AWK ao invés de Perl? Principalmente porque AWK faz parte do UNIX. +Você pode sempre contar com ele, enquanto o futuro do Perl é indefinido. AWK é +também mais fácil de ler que Perl. Para scripts simples de processamento de +texto, particularmente aqueles que leem arquivos linha por linha e fatiam texto +por delimitadores, AWK é provavelmente a ferramenta certa para a tarefa. + +```awk +#!/usr/bin/awk -f + +# Comentários são assim + +# Programas AWK consistem de uma coleção de padrões e ações. O mais +# importante padrão é chamado BEGIN. Ações estão dentro de blocos +# entre chaves. + +BEGIN { + + # O bloco BEGIN será executado no começo do programa. É onde você coloca + # todo código que prepara a execução, antes que você processe qualquer + # arquivo de texto. Se você não tem arquivos de texto, então pense no + # BEGIN como o ponto principal de entrada. + + # Variáveis são globais. Simplesmente atribua valores ou as use, sem + # necessidade de declarar. + + # Operadores são como em C e similares + a = count + 1 + b = count - 1 + c = count * 1 + d = count / 1 # divisão inteira + e = count % 1 # módulo + f = count ^ 1 # exponenciação + + a += 1 + b -= 1 + c *= 1 + d /= 1 + e %= 1 + f ^= 1 + + # Incrementando e decrementando por um + a++ + b-- + + # Como um operador pré-fixado, retorna o valor incrementado + ++a + --b + + # Perceba, não há pontuação, como ponto-e-vírgula, ao final das declarações + + # Declarações de controle + if (count == 0) + print "Começando com count em 0" + else + print "Como é que é?" + + # Ou você pode usar o operador ternário + print (count == 0) ? "Começando com count em 0" : "Como é que é?" + + # Blocos multilinhas devem usar chaves + while (a < 10) { + print "Concatenação de texto é feita" " com uma série" " de" + " textos separados por espaço" + print a + + a++ + } + + for (i = 0; i < 10; i++) + print "Uma boa opção para um loop de uma linha" + + # Quanto a comparações, eis os padrões: + a < b # Menor que + a <= b # Menor ou igual a + a != b # Não igual + a == b # Igual + a > b # Maior que + a >= b # Maior ou igual a + + # Bem como operadores lógicos + a && b # E + a || b # OU (inclusivo) + + # Em adição, há o utilíssimo operador para expressões regulares + if ("foo" ~ "^fo+$") + print "Fooey!" + if ("boo" !~ "^fo+$") + print "Boo!" + + # Matrizes + arr[0] = "foo" + arr[1] = "bar" + # Infelizmente, não há outra forma para inicializar uma matriz. Apenas + # coloque cada valor em uma linha, como mostrado acima. + + # Você também pode ter matrizes associativas + assoc["foo"] = "bar" + assoc["bar"] = "baz" + + # E matrizes multidimensionais, com algumas limitações que não mencionarei + multidim[0,0] = "foo" + multidim[0,1] = "bar" + multidim[1,0] = "baz" + multidim[1,1] = "boo" + + # Você pode testar a pertinência de um elemento em uma matriz + if ("foo" in assoc) + print "Fooey!" + + # Você pode também usar o operador 'in' para percorrer as chaves de uma + # matriz associativa + for (key in assoc) + print assoc[key] + + # Os argumentos da linha de comando estão em uma matriz especial ARGV + for (argnum in ARGV) + print ARGV[argnum] + + # Você pode remover elementos de uma matriz + # Isso é muito útil para prevenir que o AWK assuma que os argumentos são + # arquivo para ele processar + delete ARGV[1] + + # A quantidade de argumentos passados está na variável ARGC + print ARGC + + # O AWK tem várias funções nativas. Elas estão separadas em três categorias. + # Demonstrarei cada uma delas logo mais abaixo. + + return_value = arithmetic_functions(a, b, c) + string_functions() + io_functions() +} + +# Eis como você deve definir uma função +function arithmetic_functions(a, b, c, d) { + + # Provavelmente a parte mais irritante do AWK é ele não possuir variáveis + # locais. Tudo é global. Para pequenos scripts, isso não é problema, e + # pode até mesmo ser considerado útil, mas para grandes scripts, isso pode + # ser um problema. + + # Mas há como contornar isso (um hack). Os argumentos de função são locais + # para a função e o AWK permite que você defina mais argumentos de função + # do que ele precise. Então, coloque a variável local na declaração de + # função, como eu fiz acima. Como uma convenção, adicione alguns espaços + # extras para distinguir entre parâmetros de função reais e variáveis + # locais. Neste exemplo, a, b e c são parâmetros reais, enquanto d é + # meramente uma variável local. + + # Agora, serão demonstradas as funções aritméticas + + # Muitas implementações AWK possuem algumas funções trigonométricas padrão + localvar = sin(a) + localvar = cos(a) + localvar = atan2(b, a) # arco-tangente de b / a + + # E conteúdo logarítmico + localvar = exp(a) + localvar = log(a) + + # Raiz quadrada + localvar = sqrt(a) + + # Descartando a parte não inteira de um número em ponto flutuante. + localvar = int(5.34) # localvar => 5 + + # Números aleatórios + srand() # Forneça uma semente como argumento. Por padrão, ele usa a hora atual + localvar = rand() # Número aleatório entre 0 e 1. + + # Aqui mostramos como retornar um valor + return localvar +} + +function string_functions( localvar, arr) { + + # Sendo o AWK uma linguagem para processamento de texto, ele possui + # várias funções para manipulação de texto, muitas das quais + # fortemente dependentes de expressões regulares. + + # Procurar e substituir, primeira instância (sub), ou todas (gsub) + # Ambas retornam o número de instâncias substituídas + localvar = "fooooobar" + sub("fo+", "Meet me at the ", localvar) # localvar => "Meet me at the bar" + gsub("e+", ".", localvar) # localvar => "m..t m. at th. bar" + + # Localiza um texto que casa com uma expressão regular + # index() faz a mesma coisa, mas não permite uma expressão regular + match(localvar, "t") # => 4, pois 't' é o quarto carácter + + # Separa por delimitador + split("foo-bar-baz", arr, "-") # a => ["foo", "bar", "baz"] + + # Outras coisas úteis + sprintf("%s %d %d %d", "Testing", 1, 2, 3) # => "Testing 1 2 3" + substr("foobar", 2, 3) # => "oob" + substr("foobar", 4) # => "bar" + length("foo") # => 3 + tolower("FOO") # => "foo" + toupper("foo") # => "FOO" +} + +function io_functions( localvar) { + + # Você já viu como imprimir + print "Hello world" + + # Também há o printf + printf("%s %d %d %d\n", "Testing", 1, 2, 3) + + # O AWK não disponibiliza manipuladores de arquivo. Ele irá automaticamente + # manipular um arquivo quando você fizer algo que precise disso. O texto + # que você usou para isso pode ser usado como um manipulador de arquivo, + # para propósitos de E/S. Isso faz ele parecer com um shell script: + + print "foobar" >"/tmp/foobar.txt" + + # Agora a string "/tmp/foobar.txt" é um manipulador de arquivos. Você pode + # fechá-lo: + close("/tmp/foobar.txt") + + # Aqui está como você pode executar alguma coisa no shell + system("echo foobar") # => prints foobar + + # Lê uma linha da entrada padrão e armazena em localvar + getline localvar + + # Lê uma linha de um pipe + "echo foobar" | getline localvar # localvar => "foobar" + close("echo foobar") + + # Lê uma linha de um arquivo e armazena em localvar + getline localvar <"/tmp/foobar.txt" + close("/tmp/foobar.txt") +} + +# Como dito no início, os programas AWK consistem de uma coleção de padrões +# e ações. Você já viu o padrão BEGIN, o mais importante. Outros padrões são +# usados apenas se você estiver processando linhas de arquivos ou a entrada +# padrão. + +# Quando você passa argumentos para o AWK, eles são tratados como nomes de +# arquivos para processar. Todos serão processados, em ordem. Pense nisso como +# um implícito para loop, iterando sobre as linhas nesses arquivos. Esses +# padrões e ações são como instruções de mudança dentro do loop. + +/^fo+bar$/ { + + # Esta ação será executada para cada linha que corresponda à expressão + # regular, / ^ fo + bar $ /, e será ignorada para qualquer linha que não + # corresponda. Vamos apenas imprimir a linha: + + print + + # Opa, sem argumento! Isso ocorre pois print tem um argumento padrão: $0. + # $0 é o nome da linha atual que está sendo processada. Essa variável é + # criada automaticamente para você. + + # Você provavelmente pode adivinhar que existem outras variáveis $. Toda + # linha é implicitamente dividida antes de cada ação ser chamada, como + # o shell faz. E, como o shell, cada campo pode ser acessado com um sinal + # de cifrão + + # Isso irá imprimir o segundo e quarto campos da linha + print $2, $4 + + # O AWK automaticamente define muitas outras variáveis para ajudar você + # a inspecionar processar cada linha. A mais importante delas é NF. + + # Imprime o número de campos da linha atual + print NF + + # Imprime o último campo da linha atual + print $NF +} + +# Todo padrão é na verdade um teste verdadeiro/falso. A expressão regular no +# último padrão também é um teste verdadeiro/falso, mas parte dele estava +# escondido. Se você não informar um texto para testar, AWK assumirá $0, +# a linha que está atualmente sendo processada. Assim, a versão completa +# é a seguinte: + +$0 ~ /^fo+bar$/ { + print "Equivalente ao último padrão" +} + +a > 0 { + # Isso será executado uma vez para cada linha, quando a for positivo +} + +# Você entendeu. Processar arquivos de texto, ler uma linha de cada vez, e +# fazer algo com ela, particularmente dividir com base em um delimitador, é +# tão comum no UNIX que AWK é uma linguagem de script que faz tudo por você, +# sem você precisa perguntar. Tudo o que você precisa fazer é escrever os +# padrões e ações com base no que você espera da entrada, e o que você quer +# fazer com isso. + +# Aqui está um exemplo rápido de um script simples, o tipo de coisa que o AWK +# é perfeito para fazer. Ele irá ler um nome da entrada padrão e depois +# imprimirá a média de idade de todos com esse primeiro nome. Digamos que você +# forneça como argumento o nome de um arquivo com esses dados: + +# Bob Jones 32 +# Jane Doe 22 +# Steve Stevens 83 +# Bob Smith 29 +# Bob Barker 72 +# +# Eis o script: + +BEGIN { + + # Primeiro, pergunte o nome do usuário + print "Para qual nome você quer calcular a média de idade?" + + # Pega uma linha da entrada padrão, não dos arquivos indicados na + # linha de comando + getline name <"/dev/stdin" +} + +# Agora, processa cada linha em que o primeiro nome é o nome informado +$1 == name { + + # Dentro desse bloco, nós temos acesso a algumas variáveis uteis, que + # foram pré-carregadas para nós: + # $0 é a linha corrente completa + # $3 é o terceiro campo, que é o que nos interessa aqui + # NF é a quantidade de campos, que deve ser 3 + # NR é o número de registros (linhas) lidas até agora + # FILENAME é o nome do arquivo sendo processado + # FS é o delimitador em uso, que é " " aqui + # ...etc. Há muito mais, documentadas no manual. + + # Mantenha um registro do total e da quantidade de linhas encontradas + sum += $3 + nlines++ +} + +# Outro padrão especial é chamado END. Ele será executado após o processamento +# de todos os arquivos de texto. Ao contrário de BEGIN, ele só será executado +# se você tiver dado a ele dados para processar. Ele será executado depois de +# todos os arquivos terem sido lidos e processados de acordo com as regras e +# ações que você forneceu. O objetivo disso em geral é produzir algum tipo de +# relatório final, ou fazer algo com o agregado dos dados acumulados ao longo +# do script. + +END { + if (nlines) + print "A média da idade para " name " é " sum / nlines +} + +``` +Leituras adicionais (em inglês): + +* [Awk tutorial](http://www.grymoire.com/Unix/Awk.html) +* [Awk man page](https://linux.die.net/man/1/awk) +* [The GNU Awk User's Guide](https://www.gnu.org/software/gawk/manual/gawk.html) GNU AWK é encontrado na maioria dos sistemas GNU/Linux. diff --git a/pt-br/bash-pt.html.markdown b/pt-br/bash-pt.html.markdown index ae18435a..988e8e7d 100644 --- a/pt-br/bash-pt.html.markdown +++ b/pt-br/bash-pt.html.markdown @@ -16,7 +16,7 @@ lang: pt-br Tutorial de shell em português -Bash é o nome do shell do Unix, que também é distribuido como shell do sistema +Bash é o nome do shell do Unix, que também é distribuído como shell do sistema operacional GNU e como shell padrão para Linux e Mac OS X. Praticamente todos os exemplos abaixo podem fazer parte de um shell script e pode ser executados diretamente no shell. @@ -33,7 +33,7 @@ diretamente no shell. # Exemplo simples de hello world: echo Hello World! -# Cada comando começa com uma nova linha, ou após um ponto virgula: +# Cada comando começa com uma nova linha, ou após um ponto e vírgula: echo 'Essa é a primeira linha'; echo 'Essa é a segunda linha' # A declaração de variáveis é mais ou menos assim @@ -41,14 +41,14 @@ Variavel="Alguma string" # Mas não assim: Variavel = "Alguma string" -# Bash interpretará Variavel como um comando e tentará executar e lhe retornar +# Bash interpretará Variavel como um comando e tentará executar e lhe retornará # um erro porque o comando não pode ser encontrado. # Ou assim: Variavel= 'Alguma string' -# Bash interpretará 'Alguma string' como um comando e tentará executar e lhe retornar -# um erro porque o comando não pode ser encontrado. (Nesse caso a a parte 'Variavel=' -# é vista com uma declaração de variável valida apenas para o escopo do comando 'Uma string'). +# Bash interpretará 'Alguma string' como um comando e tentará executar e lhe retornará +# um erro porque o comando não pôde ser encontrado. (Nesse caso a a parte 'Variavel=' +# é vista com uma declaração de variável válida apenas para o escopo do comando 'Uma string'). # Usando a variável: echo $Variavel @@ -65,15 +65,15 @@ echo ${Variavel/Alguma/Uma} # Substring de uma variável Tamanho=7 echo ${Variavel:0:Tamanho} -# Isso retornará apenas os 7 primeiros caractéres da variável +# Isso retornará apenas os 7 primeiros caracteres da variável # Valor padrão de uma variável echo ${Foo:-"ValorPadraoSeFooNaoExistirOuEstiverVazia"} # Isso funciona para nulo (Foo=) e (Foo=""); zero (Foo=0) retorna 0. -# Note que isso apenas retornar o valor padrão e não mudar o valor da variável. +# Note que isso apenas retornará o valor padrão e não mudará o valor da variável. # Variáveis internas -# Tem algumas variáveis internas bem uteis, como +# Tem algumas variáveis internas bem úteis, como echo "O ultimo retorno do programa: $?" echo "PID do script: $$" echo "Numero de argumentos passados para o script $#" @@ -86,7 +86,7 @@ read Nome # Note que nós não precisamos declarar a variável echo Ola, $Nome # Nós temos a estrutura if normal: -# use 'man test' para mais infomações para as condicionais +# use 'man test' para mais informações para as condicionais if [ $Nome -ne $USER ] then echo "Seu nome não é o seu username" @@ -109,7 +109,7 @@ then echo "Isso vai rodar se $Nome é Daniela ou Jose." fi -# Expressões são denotadas com o seguinte formato +# Expressões são escritas com o seguinte formato echo $(( 10 + 5)) # Diferentemente das outras linguagens de programação, bash é um shell, então ele @@ -118,9 +118,9 @@ echo $(( 10 + 5)) ls #Esse comando tem opções que controlam sua execução -ls -l # Lista todo arquivo e diretorio em linhas separadas +ls -l # Lista todo arquivo e diretório em linhas separadas -# Os resultados do comando anterior pode ser passado para outro comando como input. +# Os resultados do comando anterior podem ser passados para outro comando como input. # O comando grep filtra o input com o padrão passado. É assim que listamos apenas # os arquivos .txt no diretório atual: ls -l | grep "\.txt" @@ -165,7 +165,7 @@ echo "#helloworld" | tee output.out > /dev/null rm -v output.out error.err output-and-error.log # Comando podem ser substituídos por outros comandos usando $( ): -# O comando a seguir mostra o número de arquivos e diretórios no diretorio atual +# O comando a seguir mostra o número de arquivos e diretórios no diretório atual echo "Existem $(ls | wc -l) itens aqui." # O mesmo pode ser feito usando crase `` mas elas não podem ser aninhadas - dá se @@ -241,14 +241,14 @@ head -n 10 arquivo.txt sort arquivo.txt # reporta ou omite as linhas repetidas, com -d você as reporta uniq -d arquivo.txt -# exibe apenas a primeira coluna após o caráctere ',' +# exibe apenas a primeira coluna após o caractere ',' cut -d ',' -f 1 arquivo.txt # substitui todas as ocorrencias de 'okay' por 'legal' em arquivo.txt (é compativel com regex) sed -i 's/okay/legal/g' file.txt # exibe para o stdout todas as linhas do arquivo.txt que encaixam com o regex # O exemplo exibe linhas que começam com "foo" e terminam com "bar" grep "^foo.*bar$" arquivo.txt -# passe a opção "-c" para ao invês de imprimir o numero da linha que bate com o regex +# passe a opção "-c" para ao invés de imprimir o número da linha que bate com o regex grep -c "^foo.*bar$" arquivo.txt # se você quer literalmente procurar por uma string, # e não pelo regex, use fgrep (ou grep -F) diff --git a/pt-br/bf.html.markdown b/pt-br/bf-pt.html.markdown index d6d7c6e9..53baa9a2 100644 --- a/pt-br/bf.html.markdown +++ b/pt-br/bf-pt.html.markdown @@ -1,5 +1,6 @@ --- language: bf +filename: learnbf-pt.bf contributors: - ["Prajit Ramachandran", "http://prajitr.github.io/"] - ["Mathias Bynens", "http://mathiasbynens.be/"] @@ -12,7 +13,9 @@ lang: pt-br Brainfuck (em letras minúsculas, exceto no início de frases) é uma linguagem de programação Turing-completa extremamente simples com apenas 8 comandos. -``` +Você pode experimentar brainfuck pelo seu browser com [brainfuck-visualizer](http://fatiherikli.github.io/brainfuck-visualizer/). + +```bf Qualquer caractere exceto "><+-.,[]" (sem contar as aspas) é ignorado. Brainfuck é representado por um vetor com 30 000 células inicializadas em zero diff --git a/pt-br/c++-pt.html.markdown b/pt-br/c++-pt.html.markdown index e2e95268..42a29991 100644 --- a/pt-br/c++-pt.html.markdown +++ b/pt-br/c++-pt.html.markdown @@ -1,6 +1,6 @@ --- language: c++ -filename: learncpp.cpp +filename: learncpp-pt.cpp contributors: - ["Steven Basart", "http://github.com/xksteven"] - ["Matt Kline", "https://github.com/mrkline"] @@ -18,10 +18,10 @@ foi concebida para - suportar programação orientada a objetos - suportar programação genérica -Embora sua sintaxe pode ser mais difícil ou complexa do que as linguagens mais -recentes, C++ é amplamente utilizado porque compila para instruções nativas que -podem ser executadas diretamente pelo processador e oferece um controlo rígido sobre hardware (como C), enquanto oferece recursos de alto nível, como os -genéricos, exceções e classes. Esta combinação de velocidade e funcionalidade +Embora sua sintaxe possa ser mais difícil ou complexa do que as linguagens mais +recentes, C++ é amplamente utilizada porque compila para instruções nativas que +podem ser executadas diretamente pelo processador e oferece um controle rígido sobre o hardware (como C), enquanto oferece recursos de alto nível, como os +genéricos, exceções e classes. Esta combinação de velocidade e funcionalidade faz C++ uma das linguagens de programação mais utilizadas. ```c++ @@ -33,17 +33,17 @@ faz C++ uma das linguagens de programação mais utilizadas. // declarações de variáveis, tipos primitivos, e funções. No entanto, C++ varia // em algumas das seguintes maneiras: -// A função main() em C++ deve retornar um int, embora void main() é aceita +// A função main() em C++ deve retornar um int, embora void main() é aceita // pela maioria dos compiladores (gcc, bumbum, etc.) // Este valor serve como o status de saída do programa. // Veja http://en.wikipedia.org/wiki/Exit_status para mais informações. int main(int argc, char** argv) { - // Argumentos de linha de comando são passados em pelo argc e argv da mesma + // Argumentos de linha de comando são passados para argc e argv da mesma // forma que eles estão em C. // argc indica o número de argumentos, - // e argv é um array de strings, feito C (char*) representado os argumentos + // e argv é um array de strings, feito C (char*) representando os argumentos // O primeiro argumento é o nome pelo qual o programa foi chamado. // argc e argv pode ser omitido se você não se importa com argumentos, // dando a assinatura da função de int main() @@ -105,7 +105,7 @@ int main() // Parâmetros padrão de função ///////////////////////////// -// Você pode fornecer argumentos padrões para uma função se eles não são +// Você pode fornecer argumentos padrões para uma função se eles não são // fornecidos pelo chamador. void doSomethingWithInts(int a = 1, int b = 4) @@ -157,7 +157,7 @@ void foo() int main() { - // Assuma que tudo é do namespace "Second" a menos que especificado de + // Assuma que tudo é do namespace "Second" a menos que especificado de // outra forma. using namespace Second; @@ -222,7 +222,7 @@ cout << myString; // "Hello Dog" // Além de indicadores como os de C, C++ têm _referências_. Esses são tipos de // ponteiro que não pode ser reatribuída uma vez definidos e não pode ser nulo. -// Eles também têm a mesma sintaxe que a própria variável: Não * é necessário +// Eles também têm a mesma sintaxe que a própria variável: Não * é necessário // para _dereferencing_ e & (endereço de) não é usado para atribuição. using namespace std; @@ -258,7 +258,7 @@ class Dog { std::string name; int weight; -// Todos os membros a seguir este são públicos até que "private:" ou +// Todos os membros a seguir este são públicos até que "private:" ou // "protected:" é encontrado. public: @@ -274,13 +274,13 @@ public: void setWeight(int dogsWeight); - // Funções que não modificam o estado do objecto devem ser marcadas como + // Funções que não modificam o estado do objeto devem ser marcadas como // const. Isso permite que você chamá-los se for dada uma referência const // para o objeto. Além disso, observe as funções devem ser explicitamente - // declarados como _virtual_, a fim de ser substituídas em classes - // derivadas. As funções não são virtuais por padrão por razões de + // declarados como _virtual_, a fim de ser substituídas em classes + // derivadas. As funções não são virtuais por padrão por razões de // performance. - + virtual void print() const; // As funções também podem ser definidas no interior do corpo da classe. @@ -291,7 +291,7 @@ public: // Estes são chamados quando um objeto é excluído ou fica fora do escopo. // Isto permite paradigmas poderosos, como RAII // (veja abaixo) - // Destruidores devem ser virtual para permitir que as classes de ser + // Destruidores devem ser virtual para permitir que as classes de ser // derivada desta. virtual ~Dog(); @@ -323,7 +323,7 @@ void Dog::print() const void Dog::~Dog() { - cout << "Goodbye " << name << "\n"; + std::cout << "Goodbye " << name << "\n"; } int main() { @@ -343,8 +343,8 @@ class OwnedDog : public Dog { // Substituir o comportamento da função de impressão de todas OwnedDogs. // Ver http://en.wikipedia.org/wiki/Polymorphism_(computer_science)#Subtyping - // Para uma introdução mais geral, se você não estiver familiarizado com o - // polimorfismo subtipo. A palavra-chave override é opcional, mas torna-se + // Para uma introdução mais geral, se você não estiver familiarizado com o + // polimorfismo subtipo. A palavra-chave override é opcional, mas torna-se // na verdade você está substituindo o método em uma classe base. void print() const override; @@ -371,8 +371,8 @@ void OwnedDog::print() const // Inicialização e Sobrecarga de Operadores ////////////////////////////////////////// -// Em C ++, você pode sobrecarregar o comportamento dos operadores, tais como -// +, -, *, /, etc. Isto é feito através da definição de uma função que é +// Em C ++, você pode sobrecarregar o comportamento dos operadores, tais como +// +, -, *, /, etc. Isto é feito através da definição de uma função que é // chamado sempre que o operador é usado. #include <iostream> @@ -438,7 +438,7 @@ int main () { // mas qualquer tipo pode ser jogado como uma exceção #include <exception> -// Todas as exceções lançadas dentro do bloco try pode ser capturado por +// Todas as exceções lançadas dentro do bloco try pode ser capturado por // manipuladores de captura subseqüentes try { // Não aloca exceções no heap usando _new_. @@ -460,7 +460,7 @@ catch (const std::exception& ex) /////// // RAII significa alocação de recursos é de inicialização. -// Muitas vezes, é considerado o paradigma mais poderoso em C++, e é o +// Muitas vezes, é considerado o paradigma mais poderoso em C++, e é o // conceito simples que um construtor para um objeto adquire recursos daquele // objeto e o destruidor liberá-los. @@ -479,11 +479,11 @@ void doSomethingWithAFile(const char* filename) } // Infelizmente, as coisas são levemente complicadas para tratamento de erros. -// Suponha que fopen pode falhar, e que doSomethingWithTheFile e -// doSomethingElseWithIt retornam códigos de erro se eles falharem. (As -// exceções são a forma preferida de lidar com o fracasso, mas alguns -// programadores, especialmente aqueles com um conhecimento em C, discordam -// sobre a utilidade de exceções). Agora temos que verificar cada chamada para +// Suponha que fopen pode falhar, e que doSomethingWithTheFile e +// doSomethingElseWithIt retornam códigos de erro se eles falharem. (As +// exceções são a forma preferida de lidar com o fracasso, mas alguns +// programadores, especialmente aqueles com um conhecimento em C, discordam +// sobre a utilidade de exceções). Agora temos que verificar cada chamada para // o fracasso e fechar o identificador de arquivo se ocorreu um problema. bool doSomethingWithAFile(const char* filename) @@ -564,15 +564,15 @@ void doSomethingWithAFile(const std::string& filename) // Isto tem _grandes_ vantagens: // 1. Não importa o que aconteça, -// o recurso (neste caso, o identificador de ficheiro) irá ser limpo. +// o recurso (neste caso, o identificador de ficheiro) será limpo. // Depois de escrever o destruidor corretamente, // É _impossível_ esquecer de fechar e vazar o recurso // 2. Nota-se que o código é muito mais limpo. // As alças destructor fecham o arquivo por trás das cenas // sem que você precise se preocupar com isso. // 3. O código é seguro de exceção. -// Uma exceção pode ser jogado em qualquer lugar na função e a limpeza -// irá ainda ocorrer. +// Uma exceção pode ser lançada em qualquer lugar na função e a limpeza +// ainda irá ocorrer. // Todos códigos C++ usam RAII extensivamente para todos os recursos. // Outros exemplos incluem @@ -609,7 +609,6 @@ h=sum<double>(f,g); ``` Leitura Adicional: -Uma referência atualizada da linguagem pode ser encontrada em -<http://cppreference.com/w/cpp> - -Uma fonte adicional pode ser encontrada em <http://cplusplus.com> +* Uma referência atualizada da linguagem pode ser encontrada em [CPP Reference](http://cppreference.com/w/cpp). +* Uma fonte adicional pode ser encontrada em [CPlusPlus](http://cplusplus.com). +* Um tutorial cobrindo o básico da linguagem e configurando o ambiente de codificação está disponível em [TheChernoProject - C ++](https://www.youtube.com/playlist?list=PLlrATfBNZ98dudnM48yfGUldqGD0S4FFb). diff --git a/pt-br/c-pt.html.markdown b/pt-br/c-pt.html.markdown index 0af553c8..4e55f068 100644 --- a/pt-br/c-pt.html.markdown +++ b/pt-br/c-pt.html.markdown @@ -8,6 +8,7 @@ translators: - ["João Farias", "https://github.com/JoaoGFarias"] - ["Elton Viana", "https://github.com/eltonvs"] - ["Cássio Böck", "https://github.com/cassiobsilva"] + - ["Heitor P. de Bittencourt", "https://github.com/heitorPB/"] lang: pt-br filename: c-pt.el --- @@ -182,7 +183,7 @@ int main() { int a, b, c; a = b = c = 0; - // Aritimética é óbvia + // Aritmética é óbvia i1 + i2; // => 3 i2 - i1; // => 1 i2 * i1; // => 2 @@ -191,7 +192,7 @@ int main() { f1 / f2; // => 0.5, mais ou menos epsilon // Números e cálculos de ponto flutuante não são exatos - // Modulo também existe + // Módulo também existe 11 % 3; // => 2 // Operadores de comparação provavelmente são familiares, @@ -538,7 +539,7 @@ int area(retan r) return r.largura * r.altura; } -// Se você tiver structus grande, você pode passá-las "por ponteiro" +// Se você tiver structs grandes, você pode passá-las "por ponteiro" // para evitar cópia de toda a struct: int area(const retan *r) { @@ -638,16 +639,17 @@ typedef void (*minha_função_type)(char *); ## Leitura adicional É recomendado ter uma cópia de [K&R, aka "The C Programming Language"](https://en.wikipedia.org/wiki/The_C_Programming_Language). -Este é *o* livro sobre C, escrito pelos criadores da linguage. Mas cuidado - ele é antigo e contém alguns erros (bem, -ideias que não são consideradas boas hoje) ou práticas mudadas. +Este é *o* livro sobre C, escrito pelos criadores da linguagem. Mas cuidado - ele é antigo e contém alguns erros (bem, +ideias que não são mais consideradas boas) ou práticas ultrapassadas. -Outra boa referência é [Learn C the hard way](http://c.learncodethehardway.org/book/). +Outra boa referência é [Learn C the hard way](http://learncodethehardway.org/c/). Se você tem uma pergunta, leia [compl.lang.c Frequently Asked Questions](http://c-faq.com). É importante usar espaços e indentação adequadamente e ser consistente com seu estilo de código em geral. -Código legível é melhor que código 'esperto' e rápido. Para adotar um estilo de código bom e são, veja -[Linux kernel coding stlye](https://www.kernel.org/doc/Documentation/CodingStyle). +Código legível é melhor que código 'esperto' e rápido. Para adotar um estilo de código bom e sensato, veja +[Linux kernel coding style](https://www.kernel.org/doc/Documentation/CodingStyle). Além disso, Google é teu amigo. + [1] http://stackoverflow.com/questions/119123/why-isnt-sizeof-for-a-struct-equal-to-the-sum-of-sizeof-of-each-member diff --git a/pt-br/clojure-macros-pt.html.markdown b/pt-br/clojure-macros-pt.html.markdown index d56840e0..c686bb80 100644 --- a/pt-br/clojure-macros-pt.html.markdown +++ b/pt-br/clojure-macros-pt.html.markdown @@ -13,15 +13,15 @@ do Clojure lhe dá acesso a toda a extensão da linguagem para escrever rotinas de geração de código chamados "macros". Macros fornecem uma poderosa forma de adequar a linguagem às suas necessidades. -Pórem Tenha cuidado. É considerado má pratica escrever uma macro quando uma função vai fazer. Use uma macro apenas -quando você precisar do controle sobre quando ou se os argumentos para um formulário será avaliado. +Pórem, tenha cuidado. É considerado má pratica escrever uma macro quando uma função vai fazer. Use uma macro apenas +quando você precisar de controle sobre quando ou se os argumentos de um formulário serão avaliados. Você vai querer estar familiarizado com Clojure. Certifique-se de entender tudo em -[Clojure em Y Minutos](/docs/clojure/). +[Aprenda Clojure em Y Minutos](/docs/clojure/). ```clojure -;; Defina uma macro utilizando defmacro. Sua macro deve ter como saida uma lista que possa -;; ser avaliada como codigo Clojure. +;; Defina uma macro utilizando defmacro. Sua macro deve ter como saída uma lista que possa +;; ser avaliada como código Clojure. ;; ;; Essa macro é a mesma coisa que se você escrever (reverse "Hello World") (defmacro my-first-macro [] @@ -33,14 +33,14 @@ Você vai querer estar familiarizado com Clojure. Certifique-se de entender tudo (macroexpand '(my-first-macro)) ;; -> (#<core$reverse clojure.core$reverse@xxxxxxxx> "Hello World") -;; Você pode avaliar o resultad de macroexpand diretamente: +;; Você pode avaliar o resultado de macroexpand diretamente: (eval (macroexpand '(my-first-macro))) ; -> (\d \l \o \r \W \space \o \l \l \e \H) -;; mas você deve usar esse mais suscinto, sintax como de função: +;; mas você deve usar essa sintaxe mais sucinta e familiar a funções: (my-first-macro) ; -> (\d \l \o \r \W \space \o \l \l \e \H) -;; Você pode tornar as coisas mais faceis pra você, utilizando a sintaxe de citação mais suscinta +;; Você pode tornar as coisas mais fáceis pra você, utilizando a sintaxe de citação mais suscinta ;; para criar listas nas suas macros: (defmacro my-first-quoted-macro [] '(reverse "Hello World")) diff --git a/pt-br/clojure-pt.html.markdown b/pt-br/clojure-pt.html.markdown index 7e8b3f7b..e40b8fe7 100644 --- a/pt-br/clojure-pt.html.markdown +++ b/pt-br/clojure-pt.html.markdown @@ -5,12 +5,13 @@ contributors: - ["Adam Bard", "http://adambard.com/"] translators: - ["Mariane Siqueira Machado", "https://twitter.com/mariane_sm"] + - ["Ygor Sad", "https://github.com/ysads"] lang: pt-br --- -Clojure é uma linguagem da família do Lisp desenvolvida para a JVM (máquina virtual Java). Possui uma ênfase muito mais forte em [programação funcional] (https://pt.wikipedia.org/wiki/Programa%C3%A7%C3%A3o_funcional) pura do que Common Lisp, mas inclui diversas utilidades [STM](https://en.wikipedia.org/wiki/Software_transactional_memory) para lidar com estado a medida que isso se torna necessário. +Clojure é uma linguagem da família do Lisp desenvolvida para a JVM (máquina virtual Java). Possui uma ênfase muito mais forte em [programação funcional] (https://pt.wikipedia.org/wiki/Programa%C3%A7%C3%A3o_funcional) pura do que Common Lisp, mas inclui diversos recursos [STM](https://en.wikipedia.org/wiki/Software_transactional_memory) para lidar com estado e mutabilidade, caso isso seja necessário. -Essa combinação permite gerenciar processamento concorrente de maneira muito simples, e frequentemente de maneira automática. +Essa combinação permite gerenciar processamento concorrente de maneira muito simples - frequentemente, de modo automático. (Sua versão de clojure precisa ser pelo menos 1.2) @@ -18,367 +19,552 @@ Essa combinação permite gerenciar processamento concorrente de maneira muito s ```clojure ; Comentários começam por ponto e vírgula -; Clojure é escrito em "forms", os quais são simplesmente -; listas de coisas dentro de parênteses, separados por espaços em branco. +; Código Clojure é escrito em formas - 'forms', em inglês. Tais estruturas são +; simplesmente listas de valores encapsuladas dentro de parênteses, separados por +; espaços em branco. -; O "reader" (leitor) de Clojure presume que o primeiro elemento de -; uma par de parênteses é uma função ou macro, e que os resto são argumentos. +; Ao interpretar um código em Clojure, o interpretador ou leitor - do inglês 'reader' - assume +; que o primeiro valor dentro de uma forma é uma função ou macro, de modo que os demais valores +; são seus argumentos. Isso se deve ao fato de que Clojure, por ser uma derivação de Lisp, +; usa notação prefixa (ou polonesa). -: A primeira chamada de um arquivo deve ser ns, para configurar o namespace (espaço de nomes) +; Num arquivo, a primeira chamada deve ser sempre para a função ns, +; que é responsável por definir em qual namespace o código em questão +; deve ser alocado (ns learnclojure) ; Alguns exemplos básicos: -; str cria uma string concatenando seus argumentos -(str "Hello" " " "World") ; => "Hello World" +; Aqui, str é uma função e "Olá" " " e "Mundo" são seus argumentos. O que ela faz é criar +; uma string concatenando seus argumentos. +(str "Olá" " " "Mundo") ; => "Olá Mundo" -; Cálculos são feitos de forma direta e intuitiva +; Note que espaços em branco separam os argumentos de uma função. Opcionalmente vírgulas +; podem ser usadas, se você quiser. +(str, "Olá", " ", "Mundo") ; => "Olá Mundo" + +; As operações matemáticas básicas usam os operadores de sempre (+ 1 1) ; => 2 (- 2 1) ; => 1 (* 1 2) ; => 2 (/ 2 1) ; => 2 -; Você pode comparar igualdade utilizando = +; Esses operadores aceitam um número arbitrário de argumentos +(+ 2 2 2) ; = 2 + 2 + 2 => 6 +(- 5 1 1) ; = 5 - 1 - 1 => 3 +(* 3 3 3 3) ; = 3 * 3 * 3 * 3 => 81 + +; Para verificar se dois valores são iguais, o operador = pode ser usado (= 1 1) ; => true (= 2 1) ; => false -; Negação para operações lógicas -(not true) ; => false +; Para saber se dois valores são diferentes +(not= 1 2) ; => true +(not (= 1 2)) ; => true -; Aninhar "forms" funciona como esperado +; Conforme vimos acima, é possível aninhar duas formas (+ 1 (- 3 2)) ; = 1 + (3 - 2) => 2 +(* (- 3 2) (+ 1 2)) ; = (3 - 2) * (1 + 2) => 3 + +; Se a leitura ficar comprometida, as fórmulas também podem ser escritas em múltiplas linhas +(* (- 3 2) + (+ 1 2)) ; => 3 +(* + (- 3 2) + (+ 1 2)) ; => 3 + ; Tipos ;;;;;;;;;;;;; -; Clojure usa os tipos de objetos de Java para booleanos, strings e números. -; Use `class` para inspecioná-los -(class 1) ; Literais Integer são java.lang.Long por padrão -(class 1.); Literais Float são java.lang.Double -(class ""); Strings são sempre com aspas duplas, e são java.lang.String +; Por ter interoperabilidade com Java, Clojure usa os tipos de objetos de Java para booleanos, +; strings e números. Para descobrir qual o tipo de um valor, você pode usar a função `class`: +(class 1234) ; Literais Integer são java.lang.Long por padrão +(class 1.50) ; Literais Float são java.lang.Double +(class "oi") ; Strings sempre usam aspas duplas e são java.lang.String (class false) ; Booleanos são java.lang.Boolean -(class nil); O valor "null" é chamado nil -; Se você quiser criar um lista de literais, use aspa simples para -; ela não ser avaliada -'(+ 1 2) ; => (+ 1 2) -; (que é uma abreviação de (quote (+ 1 2))) +; Tenha cuidado, ao dividir valores inteiros: +(= (/ 1 2) + (/ 1.0 2.0)) ; => false + +(class (/ 1 2)) ; => clojure.lang.Ratio +(class (/ 1.0 2.0)) ; => java.lang.Double + +; Aqui temos uma diferença em relação a Java, pois valores nulos são representados por `nil` +(class nil) ; nil -; É possível avaliar uma lista com aspa simples -(eval '(+ 1 2)) ; => 3 ; Coleções e sequências ;;;;;;;;;;;;;;;;;;; -; Listas são estruturas encadeadas, enquanto vetores são implementados como arrays. -; Listas e Vetores são classes Java também! -(class [1 2 3]); => clojure.lang.PersistentVector -(class '(1 2 3)); => clojure.lang.PersistentList +; Os dois tipos básicos de coleção são listas - "list" em inglês - e vetores - "vectors" +; no original. A principal diferença entre eles se +; dá pela implementação: +; - Vetores são implementados como arrays +; - Listas são listas ligadas +(class [1 2 3]) ; => clojure.lang.PersistentVector +(class '(1 2 3)) ; => clojure.lang.PersistentList -; Uma lista é escrita como (1 2 3), mas temos que colocar a aspa -; simples para impedir o leitor (reader) de pensar que é uma função. -; Também, (list 1 2 3) é o mesmo que '(1 2 3) +; Outra forma de declarar listas é usando a função list +(list 1 2 3) ; => '(1 2 3) -; "Coleções" são apenas grupos de dados -; Listas e vetores são ambos coleções: +; Clojure classifica conjuntos de dados de duas maneiras + +; "Coleções" são grupos simples de dados +; Tanto listas quanto vetores são coleções: (coll? '(1 2 3)) ; => true (coll? [1 2 3]) ; => true ; "Sequências" (seqs) são descrições abstratas de listas de dados. -; Apenas listas são seqs. +; Sequências - ou seqs - são conjuntos de dados com avaliação "lazy" +; Apenas listas são seqs: (seq? '(1 2 3)) ; => true (seq? [1 2 3]) ; => false -; Um seq precisa apenas prover uma entrada quando é acessada. -; Portanto, já que seqs podem ser avaliadas sob demanda (lazy) -- elas podem definir séries infinitas: -(range 4) ; => (0 1 2 3) -(range) ; => (0 1 2 3 4 ...) (uma série infinita) -(take 4 (range)) ; (0 1 2 3) +; Ter avaliação lazy significa que uma seq somente precisa prover uma informação quando +; ela for requisitada. Isso permite às seqs representar listas infinitas. +(range) ; => (0 1 2 3 4 ...) +(cycle [1 2]) ; => (1 2 1 2 1 2 ...) +(take 4 (range)) ; => (0 1 2 3) -; Use cons para adicionar um item no início de uma lista ou vetor +; A função cons é usada para adicionar um item ao início de uma lista ou vetor: (cons 4 [1 2 3]) ; => (4 1 2 3) (cons 4 '(1 2 3)) ; => (4 1 2 3) -; Conj adiciona um item em uma coleção sempre do jeito mais eficiente. -; Para listas, elas inserem no início. Para vetores, é inserido no final. +; Já conj adiciona um item em uma coleção sempre do jeito mais eficiente. +; Em listas, isso significa inserir no início. Já em vetores, ao final. (conj [1 2 3] 4) ; => [1 2 3 4] (conj '(1 2 3) 4) ; => (4 1 2 3) -; Use concat para concatenar listas e vetores +; Concatenação de coleções pode ser feita usando concat. Note que ela sempre gera uma +; seq como resultado e está sujeita a problemas de perfomance em coleções grandes, por +; conta da natureza lazy das seqs. +(concat '(1 2) [3 4]) ; => (1 2 3 4) (concat [1 2] '(3 4)) ; => (1 2 3 4) -; Use filter, map para interagir com coleções +; Outra forma de concatenar coleções é usando into. Ela não está sujeita a problemas +; com a avaliação lazy, mas o resultado final da ordem e do tipo dos argumentos passados +(into [1 2] '(3 4)) ; => [1 2 3 4] +(into '(1 2) [3 4]) ; => (4 3 1 2) + +; Note que em into a ordem dos parâmetros influencia a coleção final. +(into [1 2] '(3 4)) ; => (1 2 3 4) +(into '(1 2) [3 4]) ; => (4 3 1 2) + +; As funções filter e map podem ser usadas para interagir com as coleções. Repare que +; elas sempre retornam seqs, independentemente do tipo do seu argumento. (map inc [1 2 3]) ; => (2 3 4) -(filter even? [1 2 3]) ; => (2) +(filter even? [1 2 3 4]) ; => (2 4) + +; Use reduce reduzir coleções a um único valor. Também é possível passar um argumento +; para o valor inicial das operações +(reduce + [1 2 3]) ; = (+ (+ (+ 1 2) 3) 4) => 10 +(reduce + 10 [1 2 3 4]) ; = (+ (+ (+ (+ 10 1) 2) 3) 4) => 20 +(reduce conj [] '(3 2 1)) ; = (conj (conj (conj [] 3) 2) 1) => [3 2 1] + +; Reparou na semelhança entre listas e as chamadas de código Clojure? Isso se deve ao +; fato de que todo código clojure é escrito usando listas. É por isso que elas sempre +; são declaradas com o caracter ' na frente. Dessa forma o interpretador não tenta +; avaliá-las. +'(+ 2 3) ; cria uma lista com os elementos +, 2 e 3 +(+ 2 3) ; o interpretador chama a função + passando como argumentos 2 e 3 -; Use reduce para reduzi-los -(reduce + [1 2 3 4]) -; = (+ (+ (+ 1 2) 3) 4) -; => 10 +; Note que ' é apenas uma abreviação para a função quote. +(quote (1 2 3)) ; => '(1 2 3) + +; É possível passar uma lista para que o interpretador a avalie. Note que isso está +; sujeito ao primeiro elemento da lista ser um literal com um nome de uma função válida. +(eval '(+ 2 3)) ; => 5 +(eval '(1 2 3)) ; dá erro pois o interpretador tenta chamar a função 1, que não existe -; Reduce pode receber um argumento para o valor inicial -(reduce conj [] '(3 2 1)) -; = (conj (conj (conj [] 3) 2) 1) -; => [3 2 1] ; Funções ;;;;;;;;;;;;;;;;;;;;; -; Use fn para criar novas funções. Uma função sempre retorna -; sua última expressão. -(fn [] "Hello World") ; => fn +; Use fn para criar novas funções. Uma função sempre retorna sua última expressão. +(fn [] "Olá Mundo") ; => fn + +; Para executar suas funções, é preciso chamá-las, envolvendo-as em parênteses. +((fn [] "Olá Mundo")) ; => "Olá Mundo" + +; Como isso não é muito prático, você pode nomear funções atribuindo elas a literais. +; Isso torna muito mais fácil chamá-las: +(def ola-mundo (fn [] "Olá Mundo")) ; => fn +(ola-mundo) ; => "Olá Mundo" -; (É necessário colocar parênteses para chamá-los) -((fn [] "Hello World")) ; => "Hello World" +; Você pode abreviar esse processo usando defn: +(defn ola-mundo [] "Olá Mundo") -; Você pode atribuir valores a variáveis utilizando def -(def x 1) -x ; => 1 +; Uma função pode receber uma lista de argumentos: +(defn ola + [nome] + (str "Olá " nome)) +(ola "Jonas") ; => "Olá Jonas" -; Atribua uma função para uma var -(def hello-world (fn [] "Hello World")) -(hello-world) ; => "Hello World" +; É possível criar funções que recebam multivariadas, isto é, que aceitam números +; diferentes de argumentos: +(defn soma + ([] 0) + ([a] a) + ([a b] (+ a b))) -; Você pode abreviar esse processo usando defn -(defn hello-world [] "Hello World") +(soma) ; => 0 +(soma 1) ; => 1 +(soma 1 2) ; => 3 -; O [] é uma lista de argumentos para um função. -(defn hello [name] - (str "Hello " name)) -(hello "Steve") ; => "Hello Steve" +; Funções podem agrupar argumentos extras em uma seq: +(defn conta-args + [& args] + (str "Você passou " (count args) " argumentos: " args)) +(conta-args 1 2 3 4) ; => "Você passou 4 argumentos: (1 2 3 4)" -; Você pode ainda usar essa abreviação para criar funcões: -(def hello2 #(str "Hello " %1)) -(hello2 "Fanny") ; => "Hello Fanny" +; Você pode misturar argumentos regulares e argumentos em seq: +(defn ola-e-conta + [nome & args] + (str "Olá " nome ", você passou " (count args) " argumentos extras")) +(ola-e-conta "Maria" 1 2 3 4) ; => "Olá Maria, você passou 4 argumentos extras" -; Vocé pode ter funções multi-variadic, isto é, com um número variável de argumentos -(defn hello3 - ([] "Hello World") - ([name] (str "Hello " name))) -(hello3 "Jake") ; => "Hello Jake" -(hello3) ; => "Hello World" -; Funções podem agrupar argumentos extras em uma seq -(defn count-args [& args] - (str "You passed " (count args) " args: " args)) -(count-args 1 2 3) ; => "You passed 3 args: (1 2 3)" +; Nos exemplos acima usamos def para associar nomes a funções, mas poderíamos usá-lo +; para associar nomes a quaisquer valores: +(def xis :x) +xis ; => :x -; Você pode misturar argumentos regulares e argumentos em seq -(defn hello-count [name & args] - (str "Hello " name ", you passed " (count args) " extra args")) -(hello-count "Finn" 1 2 3) -; => "Hello Finn, you passed 3 extra args" +; Inclusive, tais literais podem possuir alguns caracteres não usuais em outras linguagens: +(def *num-resposta* 42) +(def conexao-ativa? true) +(def grito-de-medo! "AAAAAAA") +(def ->vector-vazio []) + +; É possível, inclusive, criar apelidos a nomes que já existem: +(def somar! soma) +(somar! 41 1) ; => 42 + +; Uma forma rápida de criar funções é por meio de funções anônimas. Elas são ótimas +; para manipulação de coleções e seqs, já que podem ser passadas para map, filter +; e reduce. Nessas funções, % é substituído por cada um dos items na seq ou na coleção: +(filter #(not= % nil) ["Joaquim" nil "Maria" nil "Antônio"]) ; => ("Joaquim" "Maria" "Antônio") +(map #(* % (+ % 2)) [1 2]) ; => (3 8) ; Mapas ;;;;;;;;;; -; Hash maps e array maps compartilham uma mesma interface. Hash maps são mais -; rápidos para pesquisa mas não mantém a ordem da chave. +; Existem dois tipos de mapas: hash maps e array maps. Ambos compartilham uma mesma +; interface e funções. Hash maps são mais rápidos para retornar dados, mas não mantém +; as chaves ordenadas. (class {:a 1 :b 2 :c 3}) ; => clojure.lang.PersistentArrayMap (class (hash-map :a 1 :b 2 :c 3)) ; => clojure.lang.PersistentHashMap -; Arraymaps pode automaticamente se tornar hashmaps através da maioria das -; operações se eles ficarem grandes o suficiente, portanto não há necessida de -; se preocupar com isso. - -;Mapas podem usar qualquer valor que se pode derivar um hash como chave +; Clojure converte automaticamente array maps em hash maps, por meio da maioria das +; funções de manipulação de mapas, caso eles fiquem grandes o suficiente. Não é +; preciso se preocupar com isso. - -; Mapas podem usar qualquer valor em que se pode derivar um hash como chave, -; mas normalmente palavras-chave (keywords) são melhores. -; Keywords são como strings mas com algumas vantagens. +; Chaves podem ser qualquer valor do qual possa ser obtido um hash, mas normalmente +; usam-se keywords como chave, por possuírem algumas vantagens. (class :a) ; => clojure.lang.Keyword -(def stringmap {"a" 1, "b" 2, "c" 3}) -stringmap ; => {"a" 1, "b" 2, "c" 3} +; Keywords são como strings, porém, duas keywords de mesmo valor são sempre armazenadas +; na mesma posição de memória, o que as torna mais eficientes. +(identical? :a :a) ; => true +(identical? (String. "a") (String. "a")) ; => false -(def keymap {:a 1, :b 2, :c 3}) -keymap ; => {:a 1, :c 3, :b 2} +(def mapa-strings {"a" 1 "b" 2 "c" 3}) +mapa-strings ; => {"a" 1, "b" 2, "c" 3} -; A propósito, vírgulas são sempre tratadas como espaçoes em branco e não fazem nada. +(def mapa-keywords {:a 1 :b 2 :c 3}) +mapa-keywords ; => {:a 1, :c 3, :b 2} -; Recupere o valor de um mapa chamando ele como uma função -(stringmap "a") ; => 1 -(keymap :a) ; => 1 +; Você pode usar um mapa como função para recuperar um valor dele: +(mapa-strings "a") ; => 1 +(mapa-keywords :a) ; => 1 -; Uma palavra-chave pode ser usada pra recuperar os valores de um mapa -(:b keymap) ; => 2 +; Se a chave buscada for uma keyword, ela também pode ser usada como função para recuperar +; valores. Note que isso não funciona com strings. +(:b mapa-keywords) ; => 2 +("b" mapa-strings) ; => java.lang.String cannot be cast to clojure.lang.IFn -; Não tente isso com strings -;("a" stringmap) -; => Exception: java.lang.String cannot be cast to clojure.lang.IFn +; Se você buscar uma chave que não existe, Clojure retorna nil: +(mapa-strings "d") ; => nil -; Buscar uma chave não presente retorna nil -(stringmap "d") ; => nil +; Use assoc para adicionar novas chaves em um mapa. +(def mapa-keywords-estendido (assoc mapa-keywords :d 4)) +mapa-keywords-estendido ; => {:a 1, :b 2, :c 3, :d 4} -; Use assoc para adicionar novas chaves para hash-maps -(def newkeymap (assoc keymap :d 4)) -newkeymap ; => {:a 1, :b 2, :c 3, :d 4} +; Mas lembre-se que tipos em Clojure são sempre imutáveis! Isso significa que o mapa +; inicial continua com as mesmas informações e um novo mapa, com mais dados, é criado +; a partir dele +mapa-keywords ; => {:a 1, :b 2, :c 3} -; Mas lembre-se, tipos em Clojure são sempre imutáveis! -keymap ; => {:a 1, :b 2, :c 3} +; assoc também pode ser usado para atualizar chaves: +(def outro-mapa-keywords (assoc mapa-keywords :a 0)) +outro-mapa-keywords ; => {:a 0, :b 2, :c 3} ; Use dissoc para remover chaves -(dissoc keymap :a :b) ; => {:c 3} +(dissoc mapa-keywords :a :b) ; => {:c 3} + +; Mapas também são coleções - mas não seqs! +(coll? mapa-keywords) ; => true +(seq? mapa-keywords) ; => false + +; É possível usar filter, map e qualquer outra função de coleções em mapas. +; Porém a cada iteração um vetor no formato [chave valor] vai ser passado como +; argumento. Por isso é conveniente usar funções anônimas. +(filter #(odd? (second %)) mapa-keywords) ; => ([:a 1] [:c 3]) +(map #(inc (second %)) mapa-keywords) ; => (2 3 4) ; Conjuntos ;;;;;; -(class #{1 2 3}) ; => clojure.lang.PersistentHashSet +; Conjuntos são um tipo especial de coleções que não permitem elementos repetidos. +; Eles podem ser criados com #{} ou com a função set. (set [1 2 3 1 2 3 3 2 1 3 2 1]) ; => #{1 2 3} +(class #{1 2 3}) ; => clojure.lang.PersistentHashSet -; Adicione um membro com conj -(conj #{1 2 3} 4) ; => #{1 2 3 4} +; Note que nem sempre um set vai armazenar seus elementos na ordem esperada. +(def meu-conjunto #{1 2 3}) +meu-conjunto ; => #{1 3 2} -; Remova um membro com disj -(disj #{1 2 3} 1) ; => #{2 3} +; Adição funciona normalmente com conj. +(conj meu-conjunto 4) ; => #{1 4 3 2} -; Test por existência usando set como função: -(#{1 2 3} 1) ; => 1 -(#{1 2 3} 4) ; => nil +; Remoção, no entanto, precisa ser feita com disj: +(disj meu-conjunto 1) ; => #{3 2} -; Existem muitas outras funções no namespace clojure.sets +; Para saber se um elemento está em um conjunto, use-o como função. Nesse aspecto +; conjuntos funcionam de maneira semelhante a mapas. +(meu-conjunto 1) ; => 1 +(meu-conjunto 4) ; => nil -; Forms úteis -;;;;;;;;;;;;;;;;; -; Construções lógicas em Clojure são como macros, e -; se parecem com as demais -(if false "a" "b") ; => "b" -(if false "a") ; => nil +; Condicionais e blocos +;;;;;;;;;;;;;;;;; -; Use let para criar um novo escopo associando sîmbolos a valores (bindings) +; Você pode usar um bloco let para criar um escopo local, no qual estarão disponíveis +; os nomes que você definir: (let [a 1 b 2] - (> a b)) ; => false + (+ a b)) ; => 3 -; Agrupe comandos juntos com "do" -(do - (print "Hello") - "World") ; => "World" (prints "Hello") +(let [cores {:yellow "Amarelo" :blue "Azul"} + nova-cor :red + nome-cor "Vermelho"] + (assoc cores nova-cor nome-cor)) ; => {:yellow "Amarelo", :blue "Azul", :red "Vermelho"} -; Funções tem um do implícito -(defn print-and-say-hello [name] - (print "Saying hello to " name) - (str "Hello " name)) -(print-and-say-hello "Jeff") ;=> "Hello Jeff" (prints "Saying hello to Jeff") +; Formas do tipo if aceitam três argumentos: a condição de teste, o comando a ser +; executado caso a condição seja positiva; e o comando para o caso de ela ser falsa. +(if true "a" "b") ; => "a" +(if false "a" "b") ; => "b" + +; Opcionalmente você pode não passar o último argumento, mas se a condição for falsa +; o if vai retornar nil. +(if false "a") ; => nil + +; A forma if somente aceita um comando para ser executado em cada caso. Se você +; precisar executar mais comandos, você pode usar a função do: +(if true + (do + (print "Olá ") + (print "Mundo"))) ; => escreve "Olá Mundo" na saída + +; Se você só deseja tratar o caso de sua condição ser verdadeira, o comando when é +; uma alternativa melhor. Seu comportamento é idêntico a um if sem condição negativa. +; Uma de suas vantagens é permitir a execução de vários comandos sem exigir do: +(when true "a") ; => "a" +(when true + (print "Olá ") + (print "Mundo")) ; => também escreve "Olá Mundo" na saída + +; Isso ocorre porque when possui um bloco do implícito. O mesmo se aplica a funções e +; comandos let: +(defn escreve-e-diz-xis + [nome] + (print "Diga xis, " nome) + (str "Olá " nome)) +(escreve-e-diz-xis "João") ;=> "Olá João", além de escrever "Diga xis, João" na saída. + +(let [nome "Nara"] + (print "Diga xis, " nome) + (str "Olá " nome)) ;=> "Olá João", além de escrever "Diga xis, João" na saída. -; Assim como let -(let [name "Urkel"] - (print "Saying hello to " name) - (str "Hello " name)) ; => "Hello Urkel" (prints "Saying hello to Urkel") ; Módulos ;;;;;;;;;;;;;;; -; Use "use" para poder usar todas as funções de um modulo +; Você pode usar a função use para carregar todas as funções de um módulo. (use 'clojure.set) -; Agora nós podemos usar operações com conjuntos +; Agora nós podemos usar operações de conjuntos definidas nesse módulo: (intersection #{1 2 3} #{2 3 4}) ; => #{2 3} (difference #{1 2 3} #{2 3 4}) ; => #{1} -; Você pode escolher um subconjunto de funções para importar -(use '[clojure.set :only [intersection]]) - -; Use require para importar um módulo +; Isso porém não é uma boa prática pois dificulta saber de qual módulo cada função +; veio, além de expor o código a conflitos de nomes, caso dois módulos diferentes +; definam funções com o mesmo nome. A melhor forma de referenciar módulos é por meio +; de require: (require 'clojure.string) -; Use / para chamar funções de um módulo +; Com isso podemos chamar as funções de clojure.string usando o operador / ; Aqui, o módulo é clojure.string e a função é blank? (clojure.string/blank? "") ; => true -; Você pode dar para um módulo um nome mais curto no import +; Porém isso não é muito prático, por isso é possível dar para um nome mais curto para +; o módulo ao carregá-lo: (require '[clojure.string :as str]) -(str/replace "This is a test." #"[a-o]" str/upper-case) ; => "THIs Is A tEst." -; (#"" denota uma expressão regular literal) +(str/replace "alguém quer teste?" #"[aeiou]" str/upper-case) ; => "AlgUém qUEr tEstE?" -; Você pode usar require (e até "use", mas escolha require) de um namespace utilizando :require. -; Não é necessário usar aspa simples nos seus módulos se você usar desse jeito. +; Nesse exemplo usamos também a construção #"", que delimita uma expressão regular. + +; É possível carregar outros módulos direto na definição do namespace. Note que nesse +; contexto não é preciso usar ' antes do vetor que define a importação do módulo. (ns test (:require [clojure.string :as str] [clojure.set :as set])) + +; Operadores thread +;;;;;;;;;;;;;;;;; + +; Uma das funções mais interessantes de clojure são os operadores -> e ->> - respectivamente +; thread-first e thread-last macros. Elas permitem o encadeamento de chamadas de funções, +; sendo perfeitas para melhorar a legibilidade em transformações de dados. + +; -> usa o resultado de uma chamada como o primeiro argumento da chamada à função seguinte: +(-> " uMa StRIng com! aLG_uNs ##problemas. " + (str/replace #"[!#_]" "") + (str/replace #"\s+" " ") + str/trim ; se a função só aceitar um argumento, não é preciso usar parênteses + (str/lower-case)) ; => "uma string com alguns problemas." + +; Na thread uma string com vários problemas foi passada como primeiro argumento à função +; str/replace, que criou uma nova string, a partir da original, porém somente com caracteres +; alfabéticos. Essa nova string foi passada como primeiro argumento para a chamada str/replace +; seguinte, que criou uma nova string sem espaços duplos. Essa nova string foi então passada +; como primeiro argumento para str/trim, que removeu espaços de seu início e fim, passando essa +; última string para str/lower-case, que a converteu para caracteres em caixa baixa. + +; ->> é equivalente a ->, porém o retorno de cada função é passado como último argumento da +; função seguinte. Isso é particularmente útil para lidar com seqs, já que as funções que +; as manipulam sempre as tomam como último argumento. +(->> '(1 2 3 4) + (filter even?) ; => '(2 4) + (map inc) ; => '(3 5) + (reduce *)) ; => 15 + + ; Java ;;;;;;;;;;;;;;;;; -; Java tem uma biblioteca padrão enorme e muito útil, -; portanto é importante aprender como utiliza-la. +; A biblioteca padrão de Java é enorme e possui inúmeros algoritmos e estruturas de +; dados já implementados. Por isso é bastante conveniente saber como usá-la dentro +; de Clojure. -; Use import para carregar um modulo java +; Use import para carregar um módulo Java. (import java.util.Date) -; Você pode importar usando ns também. +; Você pode importar classes Java dentro de ns também: (ns test (:import java.util.Date - java.util.Calendar)) + java.util.Calendar + java.util.ArrayList)) ; Use o nome da clase com um "." no final para criar uma nova instância -(Date.) ; <a date object> +(def instante (Date.)) +(class instante) => ; java.util.Date + +; Para chamar um método, use o operador . com o nome do método. Outra forma é +; usar simplesmente .<nome do método> +(. instante getTime) ; => retorna um inteiro representando o instante +(.getTime instante) ; => exatamente o mesmo que acima + +; Para chamar métodos estáticos dentro de classes Java, use / +(System/currentTimeMillis) ; => retorna um timestamp -; Use . para chamar métodos. Ou, use o atalho ".method" -(. (Date.) getTime) ; <a timestamp> -(.getTime (Date.)) ; exatamente a mesma coisa. +; Note que não é preciso importar o módulo System, pois ele está sempre presente -; Use / para chamar métodos estáticos -(System/currentTimeMillis) ; <a timestamp> (o módulo System está sempre presente) +; Caso queira submeter uma instância de uma classe mutável a uma sequência de operações, +; você pode usar a função doto. Ela é funciona de maneira semelhante à função -> - ou +; thread-first -, exceto pelo fato de que ele opera com valores mutáveis. +(doto (java.util.ArrayList.) + (.add 11) + (.add 3) + (.add 7) + (java.util.Collections/sort)) ; => #<ArrayList [3, 7, 11]> -; Use doto para pode lidar com classe (mutáveis) de forma mais tolerável -(import java.util.Calendar) -(doto (Calendar/getInstance) - (.set 2000 1 1 0 0 0) - .getTime) ; => A Date. set to 2000-01-01 00:00:00 ; STM ;;;;;;;;;;;;;;;;; -; Software Transactional Memory é o mecanismo que Clojure usa para gerenciar -; estado persistente. Tem algumas construções em Clojure que o utilizam. +; Até aqui usamos def para associar nomes a valores. Isso, no entanto, possui algumas +; limitações, já que, uma vez definido essa associação, não podemos alterar o valor +; para o qual um nome aponta. Isso significa que nomes definidos com def não se +; comportam como as variáveis de outras linguagens. -; O atom é o mais simples. Passe pra ele um valor inicial -(def my-atom (atom {})) +; Para lidar com estado persistente e mutação de valores, Clojure usa o mecanismo Software +; Transactional Memory. O atom é o mais simples de todos. Passe pra ele um valor inicial e +; e ele criará um objeto que é seguro de atualizar: +(def atom-mapa (atom {})) -; Atualize o atom com um swap!. -; swap! pega uma funçnao and chama ela com o valor atual do atom -; como primeiro argumento, e qualquer argumento restante como o segundo -(swap! my-atom assoc :a 1) ; Coloca o valor do átomo my-atom como o resultado de (assoc {} :a 1) -(swap! my-atom assoc :b 2) ; Coloca o valor do átomo my-atom como o resultado de (assoc {:a 1} :b 2) +; Para acessar o valor de um atom, você pode usar a função deref ou o operador @: +@atom-mapa ; => {} +(deref atom-mapa) ; => {} -; Use '@' para desreferenciar um atom e acessar seu valor -my-atom ;=> Atom<#...> (Retorna o objeto do Atom) -@my-atom ; => {:a 1 :b 2} +; Para mudar o valor de um atom, você deve usar a função swap! +; O que ela faz é chamar a função passada usando o atom como seu primeiro argumento. Com +; isso, ela altera o valor do atom de maneira segura. +(swap! atom-mapa assoc :a 1) ; Atribui a atom-mapa o resultado de (assoc {} :a 1) +(swap! atom-mapa assoc :b 2) ; Atribui a atom-mapa o resultado de (assoc {:a 1} :b 2) -; Abaixo um contador simples usando um atom -(def counter (atom 0)) -(defn inc-counter [] - (swap! counter inc)) +; Observe que essas chamadas alteraram de fato o valor de atom-mapa. Seu novo valor é: +@atom-mapa ; => {:a 1 :b 2} -(inc-counter) -(inc-counter) -(inc-counter) -(inc-counter) -(inc-counter) +; Isso é diferente de fazer: +(def atom-mapa-2 (atom {})) +(def atom-mapa-3 (assoc @atom-mapa-2 :a 1)) -@counter ; => 5 +; Nesse exemplo, atom-mapa-2 permanece com o seu valor original e é gerado um novo mapa, +; atom-mapa-3, que contém o valor de atom-mapa-2 atualizado. Note que atom-mapa-3 é um +; simples mapa, e não uma instância de um atom +@atom-mapa-2 ; => {} +atom-mapa-3 ; => {:a 1} -; Outras construção STM são refs e agents. +(class atom-mapa-2) ; => clojure.lang.Atom +(class atom-mapa-3) ; => clojure.lang.PersistentArrayMap + +; A ideia é que o valor do atom só será atualizado se, após ser executada a função passada +; para swap!, o atom ainda estiver com o mesmo valor de antes. Isto é, se durante a execução +; da função alguém alterar o valor do atom, swap! reexecutará a função recebida usando o valor +; atual do átoma como argumento. + +; Isso é ótimo em situações nas quais é preciso garantir a consistência de algum valor - tais +; como sistemas bancários e sites de compra. Para mais exemplos e informações sobre outras +; construções STM: + +; Exemplos e aplicações: https://www.braveclojure.com/zombie-metaphysics/ ; Refs: http://clojure.org/refs ; Agents: http://clojure.org/agents ``` ### Leitura adicional -Esse tutorial está longe de ser exaustivo, mas deve ser suficiente para que você possa começar. +Esse tutorial está longe de ser completo, mas deve ser suficiente para que você possa dar seus primeiros passos em Clojure. +Caso queira aprender mais: -Clojure.org tem vários artigos: +* clojure.org tem vários artigos: [http://clojure.org/](http://clojure.org/) -Clojuredocs.org tem documentação com exemplos para quase todas as funções principais (pertecentes ao core): +* Brave Clojure possui um e-book que explora em profundidade diversos recursos de clojure, incluindo ótimos exemplos: +[https://www.braveclojure.com/](https://www.braveclojure.com/) + +* clojuredocs.org tem documentação com exemplos para quase todas as funções principais (pertecentes ao core): [http://clojuredocs.org/quickref/Clojure%20Core](http://clojuredocs.org/quickref/Clojure%20Core) -4Clojure é um grande jeito de aperfeiçoar suas habilidades em Clojure/Programação Funcional: +* 4clojure possui alguns problemas e desafios interessantes para quem quiser treinar clojure ou programação funcional: [http://www.4clojure.com/](http://www.4clojure.com/) -Clojure-doc.org tem um bom número de artigos para iniciantes: +* clojure-doc.org tem um bom número de artigos para iniciantes: [http://clojure-doc.org/](http://clojure-doc.org/) + +Clojure for the Brave and True é um livro de introdução ao Clojure e possui uma versão gratuita online: +[https://www.braveclojure.com/clojure-for-the-brave-and-true/](https://www.braveclojure.com/clojure-for-the-brave-and-true/) diff --git a/pt-br/cmake-pt.html.markdown b/pt-br/cmake-pt.html.markdown new file mode 100644 index 00000000..d11fe4f4 --- /dev/null +++ b/pt-br/cmake-pt.html.markdown @@ -0,0 +1,179 @@ +--- +category: tool +tool: cmake +contributors: + - ["Bruno Alano", "https://github.com/brunoalano"] +filename: CMake-br +translators: + - ["Lucas Pugliesi", "https://github.com/fplucas"] +lang: pt-br +--- + +CMake é um programa de compilação open-source e multiplataforma. Essa ferramenta +permitirá testar, compilar e criar pacotes a partir do seu código fonte. + +O problema que o CMake tenta resolver são os problemas de configurar os Makefiles +e Autoconfigure (diferente dos interpretadores make que tem comandos diferentes) +e sua facilidade de uso envolvendo bibliotecas terceiras. + +CMake é um sistema open-source extensível que gerencia o processo de build em um +sistema operacional e um método independente de compilador. Diferente de sistemas +multiplataformas, CMake é designado a usar em conjunto ao ambiente de compilação +nativo. Seus simples arquivos de configuração localizados em seus diretórios +(chamados arquivos CMakeLists.txt) que são usados para gerar padrões de arquivos +de compilação (ex: makefiles no Unix e projetos em Windows MSVC) que são usados +de maneira simples. + +```cmake +# No CMake, isso é um comentário + +# Para rodar nosso código, iremos utilizar esses comandos: +# - mkdir build && cd build +# - cmake .. +# - make +# +# Com esses comandos, iremos seguir as melhores práticas para compilar em um +# subdiretório e na segunda linha pediremos ao CMake para gerar um novo Makefile +# independente de sistema operacional. E finalmente, rodar o comando make. + +#------------------------------------------------------------------------------ +# Básico +#------------------------------------------------------------------------------ +# +# O arquivo CMake deve ser chamado de "CMakeLists.txt". + +# Configura a versão mínima requerida do CMake para gerar o Makefile +cmake_minimum_required (VERSION 2.8) + +# Exibe FATAL_ERROR se a versão for menor que 2.8 +cmake_minimum_required (VERSION 2.8 FATAL_ERROR) + +# Configuramos o nome do nosso projeto. Mas antes disso, iremos alterar alguns +# diretórios em nome da convenção gerada pelo CMake. Podemos enviar a LANG do +# código como segundo parâmetro +project (learncmake C) + +# Configure o diretório do código do projeto (somente convenção) +set( LEARN_CMAKE_SOURCE_DIR ${CMAKE_CURRENT_SOURCE_DIR} ) +set( LEARN_CMAKE_BINARY_DIR ${CMAKE_CURRENT_BINARY_DIR} ) + +# Isso é muito útil para configurar a versão do nosso código no sistema de compilação +# usando um estilo `semver` +set (LEARN_CMAKE_VERSION_MAJOR 1) +set (LEARN_CMAKE_VERSION_MINOR 0) +set (LEARN_CMAKE_VERSION_PATCH 0) + +# Envie as variáveis (número da versão) para o cabeçalho de código-fonte +configure_file ( + "${PROJECT_SOURCE_DIR}/TutorialConfig.h.in" + "${PROJECT_BINARY_DIR}/TutorialConfig.h" +) + +# Inclua Diretórios +# No GCC, isso irá invocar o comando "-I" +include_directories( include ) + +# Onde as bibliotecas adicionais estão instaladas? Nota: permite incluir o path +# aqui, na sequência as checagens irão resolver o resto +set( CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${CMAKE_SOURCE_DIR}/CMake/modules/" ) + +# Condições +if ( CONDICAO ) + # reposta! + + # Informação incidental + message(STATUS "Minha mensagem") + + # Aviso CMake, continua processando + message(WARNING "Minha mensagem") + + # Aviso (dev) CMake, continua processando + message(AUTHOR_WARNING "Minha mensagem") + + # Erro CMake, continua processando, mas pula a geração + message(SEND_ERROR "Minha mensagem") + + # Erro CMake, para o processamento e a geração + message(FATAL_ERROR "Minha mensagem") +endif() + +if( CONDICAO ) + +elseif( CONDICAO ) + +else( CONDICAO ) + +endif( CONDICAO ) + +# Loops +foreach(loop_var arg1 arg2 ...) + COMANDO1(ARGS ...) + COMANDO2(ARGS ...) + ... +endforeach(loop_var) + +foreach(loop_var RANGE total) +foreach(loop_var RANGE start stop [step]) + +foreach(loop_var IN [LISTS [list1 [...]]] + [ITEMS [item1 [...]]]) + +while(condicao) + COMANDO1(ARGS ...) + COMANDO2(ARGS ...) + ... +endwhile(condicao) + + +# Operações Lógicas +if(FALSE AND (FALSE OR TRUE)) + message("Não exiba!") +endif() + +# Configure um cache normal, ou uma variável de ambiente com o dado valor. +# Se a opção PARENT_SCOPE for informada em uma variável que será setada no escopo +# acima do escopo corrente. +# `set(<variavel> <valor>... [PARENT_SCOPE])` + +# Como refencia variáveis dentro de aspas ou não, argumentos com strings vazias +# não serão setados +${nome_da_variavel} + +# Listas +# Configure a lista de arquivos código-fonte +set( LEARN_CMAKE_SOURCES + src/main.c + src/imagem.c + src/pather.c +) + +# Chama o compilador +# +# ${PROJECT_NAME} referencia ao Learn_CMake +add_executable( ${PROJECT_NAME} ${LEARN_CMAKE_SOURCES} ) + +# Linka as bibliotecas +target_link_libraries( ${PROJECT_NAME} ${LIBS} m ) + +# Onde as bibliotecas adicionais serão instaladas? Nota: nos permite incluir o path +# aqui, em seguida os testes irão resolver o restante +set( CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${CMAKE_SOURCE_DIR}/CMake/modules/" ) + +# Condição do compilador (gcc ; g++) +if ( "${CMAKE_C_COMPILER_ID}" STREQUAL "GNU" ) + message( STATUS "Setting the flags for ${CMAKE_C_COMPILER_ID} compiler" ) + add_definitions( --std=c99 ) +endif() + +# Checa o Sistema Operacional +if( UNIX ) + set( LEARN_CMAKE_DEFINITIONS + "${LEARN_CMAKE_DEFINITIONS} -Wall -Wextra -Werror -Wno-deprecated-declarations -Wno-unused-parameter -Wno-comment" ) +endif() +``` + +### Mais Recursos + ++ [cmake tutorial](https://cmake.org/cmake-tutorial/) ++ [cmake documentation](https://cmake.org/documentation/) ++ [mastering cmake](http://amzn.com/1930934319/) diff --git a/pt-br/coffeescript-pt.html.markdown b/pt-br/coffeescript-pt.html.markdown index 8b1094b1..7129a463 100644 --- a/pt-br/coffeescript-pt.html.markdown +++ b/pt-br/coffeescript-pt.html.markdown @@ -3,19 +3,20 @@ language: coffeescript contributors: - ["Tenor Biel", "http://github.com/L8D"] - ["Xavier Yao", "http://github.com/xavieryao"] + - ["Claudio Busatto", "http://github.com/cjcbusatto"] translators: - ["Miguel Araújo", "https://github.com/miguelarauj1o"] lang: pt-br filename: learncoffeescript-pt.coffee --- -CoffeeScript é uma pequena linguagem que compila um-para-um para o JavaScript -equivalente, e não há interpretação em tempo de execução. Como um dos sucessores -de JavaScript, CoffeeScript tenta o seu melhor para exibir uma saída legível, -bem-impressa e bom funcionamento dos códigos JavaScript em todo o tempo de +CoffeeScript é uma pequena linguagem que compila um-para-um para o JavaScript +equivalente, e não há interpretação em tempo de execução. Como um dos sucessores +de JavaScript, CoffeeScript tenta o seu melhor para exibir uma saída legível, +bem-impressa e bom funcionamento dos códigos JavaScript em todo o tempo de execução JavaScript. -Veja também [site do CoffeeScript](http://coffeescript.org/), que tem um tutorial +Veja também [site do CoffeeScript](http://coffeescript.org/), que tem um tutorial completo sobre CoffeeScript. ``` coffeescript @@ -23,35 +24,35 @@ completo sobre CoffeeScript. #Segue as tendências de muitas linguagens modernas #Assim, os comentários são iguais a Ruby e Python, eles usam símbolos numéricos. -### -Os comentários em bloco são como estes, e eles traduzem diretamente para '/ *'s e +### +Os comentários em bloco são como estes, e eles traduzem diretamente para '/ *'s e '* /'s para o código JavaScript que resulta... -Você deveria entender mais de semântica de JavaScript antes de continuar... +Você deveria entender mais de semântica de JavaScript antes de continuar... ### -# Tarefa: -numero = 42 #=> número var = 42; +# Tarefa: +numero = 42 #=> var numero = 42; oposto = true #=> var oposto = true; -# Condições: -numero = -42 if oposto #=> if (oposto) {número = -42;} +# Condições: +numero = -42 if oposto #=> if (oposto) {numero = -42;} -# Funções: +# Funções: quadrado = (x) -> x * x #=> var quadrado = function (x) {return x * x;} -preencher = (recipiente, líquido = "coffee") -> - "Preenchendo o #{recipiente} with #{líquido}..." +preencher = (recipiente, liquido = "coffee") -> + "Preenchendo o #{recipiente} with #{liquido}..." #=>var preencher; # -#preencher = function(recipiente, líquido) { -# if (líquido == null) { -# líquido = "coffee"; +#preencher = function(recipiente, liquido) { +# if (liquido == null) { +# liquido = "coffee"; # } -# return "Preenchendo o " + recipiente + " with " + líquido + "..."; +# return "Preenchendo o " + recipiente + " with " + liquido + "..."; #}; -# Alcances: +# Alcances: list = [1 .. 5] #=> lista var = [1, 2, 3, 4, 5]; # Objetos: @@ -79,7 +80,7 @@ alert "Eu sabia!" if elvis? #=> if(typeof elvis !== "undefined" && elvis !== null) { alert("Eu sabia!"); } # Compressão de Matrizes: -cubes = (math.cube num for num in list) +cubes = (math.cube num for num in list) #=>cubes = (function() { # var _i, _len, _results; # _results = []; @@ -99,8 +100,9 @@ eat alimento for alimento in comidas when alimento isnt 'chocolate' # if (alimento !== 'chocolate') { # eat(alimento); # } +``` ## Recursos adicionais - [Smooth CoffeeScript](http://autotelicum.github.io/Smooth-CoffeeScript/) -- [CoffeeScript Ristretto](https://leanpub.com/coffeescript-ristretto/read)
\ No newline at end of file +- [CoffeeScript Ristretto](https://leanpub.com/coffeescript-ristretto/read) diff --git a/pt-br/common-lisp-pt.html.markdown b/pt-br/common-lisp-pt.html.markdown index 03a7c15c..c22cfd8e 100644 --- a/pt-br/common-lisp-pt.html.markdown +++ b/pt-br/common-lisp-pt.html.markdown @@ -19,7 +19,7 @@ Outro livro recente e popular é o [Land of Lisp](http://landoflisp.com/). -```common_lisp +```lisp ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; 0. Sintaxe diff --git a/pt-br/csharp.html.markdown b/pt-br/csharp-pt.html.markdown index 547f4817..384ca325 100644 --- a/pt-br/csharp.html.markdown +++ b/pt-br/csharp-pt.html.markdown @@ -6,23 +6,23 @@ contributors: lang: pt-br --- -C# é uma linguagem elegante e altamente tipado orientada a objetos que permite aos desenvolvedores criarem uma variedade de aplicações seguras e robustas que são executadas no .NET Framework. +C# é uma linguagem elegante, altamente tipada e orientada a objetos que permite aos desenvolvedores criar uma variedade de aplicações seguras e robustas que são executadas no .NET Framework. -[Read more here.](http://msdn.microsoft.com/pt-br/library/vstudio/z1zx9t92.aspx) +[Leia mais aqui.](http://msdn.microsoft.com/pt-br/library/vstudio/z1zx9t92.aspx) ```c# -// Comentário de linha única começa com // +// Comentários de linha única começam com // /* -Múltipas linhas é desta forma +Comentários de múltiplas linhas são desta forma */ /// <summary> -/// Esta é uma documentação comentário XML que pode ser usado para gerar externo -/// documentação ou fornecer ajuda de contexto dentro de um IDE +/// Este é um comentário de documentação XML que pode ser usado para gerar documentação +/// externa ou para fornecer ajuda de contexto dentro de uma IDE /// </summary> //public void MethodOrClassOrOtherWithParsableHelp() {} -// Especificar qual namespace seu código irá usar -// Os namespaces a seguir são padrões do .NET Framework Class Library +// Especifica os namespaces que o código irá usar +// Os namespaces a seguir são padrões da biblioteca de classes do .NET Framework using System; using System.Collections.Generic; using System.Dynamic; @@ -33,11 +33,11 @@ using System.IO; // Mas este aqui não é : using System.Data.Entity; -// Para que consiga utiliza-lo, você precisa adicionar novas referências +// Para que consiga utilizá-lo, você precisa adicionar novas referências // Isso pode ser feito com o gerenciador de pacotes NuGet : `Install-Package EntityFramework` -// Namespaces são escopos definidos para organizar o códgo em "pacotes" or "módulos" -// Usando este código a partir de outra arquivo de origem: using Learning.CSharp; +// Namespaces são escopos definidos para organizar o código em "pacotes" ou "módulos" +// Usando este código a partir de outro arquivo de origem: using Learning.CSharp; namespace Learning.CSharp { // Cada .cs deve conter uma classe com o mesmo nome do arquivo @@ -59,7 +59,7 @@ namespace Learning.CSharp Console.Write("World"); /////////////////////////////////////////////////// - // Tpos e Variáveis + // Tipos e Variáveis // // Declare uma variável usando <tipo> <nome> /////////////////////////////////////////////////// @@ -78,15 +78,17 @@ namespace Learning.CSharp short fooShort = 10000; ushort fooUshort = 10000; - // Integer - 32-bit integer + // Integer - inteiro de 32 bits int fooInt = 1; // (-2,147,483,648 <= int <= 2,147,483,647) uint fooUint = 1; // (0 <= uint <= 4,294,967,295) - + //Números por padrão são int ou uint, dependendo do tamanho. + // Long - 64-bit integer long fooLong = 100000L; // (-9,223,372,036,854,775,808 <= long <= 9,223,372,036,854,775,807) ulong fooUlong = 100000L; // (0 <= ulong <= 18,446,744,073,709,551,615) - // Numbers default to being int or uint depending on size. - // L is used to denote that this variable value is of type long or ulong + + // Números por padrão são int ou uint dependendo do tamanho. + // L é usado para denotar que o valor da variável é do tipo long ou ulong. // Double - Double-precision 64-bit IEEE 754 Floating Point double fooDouble = 123.4; // Precision: 15-16 digits @@ -95,8 +97,8 @@ namespace Learning.CSharp float fooFloat = 234.5f; // Precision: 7 digits // f is used to denote that this variable value is of type float - // Decimal - a 128-bits data type, with more precision than other floating-point types, - // suited for financial and monetary calculations + // Decimal - um tipo de dados de 128 bits, com mais precisão do que outros tipos de ponto flutuante, + // adequado para cálculos financeiros e monetários decimal fooDecimal = 150.3m; // Boolean - true & false @@ -294,9 +296,9 @@ on a new line! ""Wow!"", the masses cried"; case 3: monthString = "March"; break; - // You can assign more than one case to an action - // But you can't add an action without a break before another case - // (if you want to do this, you would have to explicitly add a goto case x + // Você pode declarar mais de um "case" para uma ação + // Mas você não pode adicionar uma ação sem um "break" antes de outro "case" + // (se você quiser fazer isso, você tem que explicitamente adicionar um "goto case x") case 6: case 7: case 8: @@ -308,25 +310,26 @@ on a new line! ""Wow!"", the masses cried"; } /////////////////////////////////////// - // Converting Data Types And Typecasting + // Convertendo Data Types e Typecasting /////////////////////////////////////// - // Converting data + // Convertendo dados + + // Converter String para Integer - // Convert String To Integer - // this will throw a FormatException on failure - int.Parse("123");//returns an integer version of "123" + // isso vai jogar um erro FormatException quando houver falha + int.Parse("123");//retorna uma verão em Integer da String "123" - // try parse will default to type default on failure - // in this case: 0 + // try parse vai ir por padrão para o typo default quando houver uma falha + // nesse caso: 0 int tryInt; - if (int.TryParse("123", out tryInt)) // Function is boolean + if (int.TryParse("123", out tryInt)) // Função booleana Console.WriteLine(tryInt); // 123 - // Convert Integer To String - // Convert class has a number of methods to facilitate conversions + // Converter Integer para String + // A classe Convert possuí métodos para facilitar as conversões Convert.ToString(123); - // or + // ou tryInt.ToString(); // Casting @@ -336,28 +339,28 @@ on a new line! ""Wow!"", the masses cried"; } /////////////////////////////////////// - // CLASSES - see definitions at end of file + // CLASSES - Veja definições no fim do arquivo /////////////////////////////////////// public static void Classes() { - // See Declaration of objects at end of file + // Veja Declaração de objetos no fim do arquivo - // Use new to instantiate a class + // Use new para instanciar uma classe Bicycle trek = new Bicycle(); - // Call object methods - trek.SpeedUp(3); // You should always use setter and getter methods + // Chame métodos do objeto + trek.SpeedUp(3); // Você deve sempre usar métodos setter e getter trek.Cadence = 100; - // ToString is a convention to display the value of this Object. + // ToString é uma convenção para exibir o valor desse Objeto. Console.WriteLine("trek info: " + trek.Info()); - // Instantiate a new Penny Farthing + // Instancie um novo Penny Farthing PennyFarthing funbike = new PennyFarthing(1, 10); Console.WriteLine("funbike info: " + funbike.Info()); Console.Read(); - } // End main method + } // Fim do método principal // CONSOLE ENTRY A console application must have a main method as an entry point public static void Main(string[] args) @@ -407,12 +410,12 @@ on a new line! ""Wow!"", the masses cried"; return result; } - // You can narrow down the objects that are passed in + // Você pode pode restringir os objetos que são passados public static void IterateAndPrint<T>(T toPrint) where T: IEnumerable<int> { - // We can iterate, since T is a IEnumerable + // Nos podemos iterar, desde que T seja um "IEnumerable" foreach (var item in toPrint) - // Item is an int + // Item é um inteiro Console.WriteLine(item.ToString()); } @@ -522,7 +525,7 @@ on a new line! ""Wow!"", the masses cried"; foreach (var key in responses.Keys) Console.WriteLine("{0}:{1}", key, responses[key]); - // DYNAMIC OBJECTS (great for working with other languages) + // OBJETOS DINÂMICOS (ótimo para trabalhar com outros idiomas) dynamic student = new ExpandoObject(); student.FirstName = "First Name"; // No need to define class first! @@ -720,9 +723,9 @@ on a new line! ""Wow!"", the masses cried"; _speed -= decrement; } - // properties get/set values - // when only data needs to be accessed, consider using properties. - // properties may have either get or set, or both + // propriedade recupera e/ou atribui valores (get/set). + // quando os dados precisam apenas ser acessados, considere o uso de propriedades. + // uma propriedade pode ter "get" ou "set", ou ambos. private bool _hasTassles; // private variable public bool HasTassles // public accessor { @@ -730,10 +733,10 @@ on a new line! ""Wow!"", the masses cried"; set { _hasTassles = value; } } - // You can also define an automatic property in one line - // this syntax will create a backing field automatically. - // You can set an access modifier on either the getter or the setter (or both) - // to restrict its access: + // Você também pode definir uma propriedade automática em uma linha + // Esta sintaxe criará um campo de apoio automaticamente. + // Você pode definir um modificador de acesso no getter ou no setter (ou ambos) + // para restringir seu acesso: public bool IsBroken { get; private set; } // Properties can be auto-implemented @@ -762,7 +765,7 @@ on a new line! ""Wow!"", the masses cried"; } } - //Method to display the attribute values of this Object. + //Método para exibir os valores dos atributos deste objeto. public virtual string Info() { return "Gear: " + Gear + @@ -784,13 +787,13 @@ on a new line! ""Wow!"", the masses cried"; } // end class Bicycle - // PennyFarthing is a subclass of Bicycle + // PennyFarthing é uma subclasse de Bicycle class PennyFarthing : Bicycle { - // (Penny Farthings are those bicycles with the big front wheel. - // They have no gears.) + // (Penny Farthings são aquelas bicicletas com uma grande roda frontal. + // Elas não tem correias.) - // calling parent constructor + // chamando construtor pai public PennyFarthing(int startCadence, int startSpeed) : base(startCadence, startSpeed, 0, "PennyFarthing", true, BikeBrand.Electra) { @@ -823,10 +826,10 @@ on a new line! ""Wow!"", the masses cried"; } } - // Interfaces only contain signatures of the members, without the implementation. + // Interfaces contêm apenas as assinaturas dos membros, sem a implementação. interface IJumpable { - void Jump(int meters); // all interface members are implicitly public + void Jump(int meters); // todos os membros da interface são implicitamente públicos } interface IBreakable @@ -834,7 +837,7 @@ on a new line! ""Wow!"", the masses cried"; bool Broken { get; } // interfaces can contain properties as well as methods & events } - // Class can inherit only one other class, but can implement any amount of interfaces + // Classes podem herdar apenas de uma outra classe, mas podem implementar qualquer quantidade de interfaces. class MountainBike : Bicycle, IJumpable, IBreakable { int damage = 0; @@ -854,8 +857,8 @@ on a new line! ""Wow!"", the masses cried"; } /// <summary> - /// Used to connect to DB for LinqToSql example. - /// EntityFramework Code First is awesome (similar to Ruby's ActiveRecord, but bidirectional) + /// Exemplo de como conectar-se ao DB via LinqToSql. + /// EntityFramework First Code é impressionante (semelhante ao ActiveRecord de Ruby, mas bidirecional) /// http://msdn.microsoft.com/en-us/data/jj193542.aspx /// </summary> public class BikeRepository : DbContext diff --git a/pt-br/css-pt.html.markdown b/pt-br/css-pt.html.markdown index b1fbd961..e6dea5b8 100644 --- a/pt-br/css-pt.html.markdown +++ b/pt-br/css-pt.html.markdown @@ -9,23 +9,25 @@ contributors: - ["Deepanshu Utkarsh", "https://github.com/duci9y"] translators: - ["Gabriel Gomes", "https://github.com/gabrielgomesferraz"] + - ["Gabriele Luz", "https://github.com/gabrieleluz"] + lang: pt-br --- -Nos primeiros dias da web não havia elementos visuais, apenas texto puro. Mas com maior desenvolvimento de navegadores da web, páginas web totalmente visuais também se tornou comum. +No início da web não havia elementos visuais, apenas texto puro. Mas com maior desenvolvimento de navegadores da web, páginas web totalmente visuais também se tornaram comuns. -CSS ajuda a manter a separação entre o conteúdo (HTML) e o look-and-feel de uma página web. +CSS ajuda a manter a separação entre o conteúdo (HTML) e o visual de uma página web. CSS permite atingir diferentes elementos em uma página HTML e atribuir diferentes propriedades visuais para eles. -Este guia foi escrito para CSS2, embora CSS3 está rapidamente se tornando popular. +Este guia foi escrito para CSS2, embora CSS3 esteja rapidamente se tornando popular. -**NOTA:** Porque CSS produz resultados visuais, a fim de aprender, você precisa tentar de tudo em um playground CSS como [dabblet](http://dabblet.com/). +**NOTA:** Porque CSS produz resultados visuais, a fim de aprender, você precisa treinar em um playground CSS como [dabblet](http://dabblet.com/). O foco principal deste artigo é sobre a sintaxe e algumas dicas gerais. ```css /* Comentários aparecem dentro do slash-asterisk, tal como esta linha! - não há "comentários de uma linha"; este é o único estilo de comentário * / + Não há "comentários de uma linha"; este é o único estilo de comentário * / /* #################### ## SELETORES @@ -40,7 +42,7 @@ Abaixo um elemento de exemplo: <div class='class1 class2' id='anID' attr='value' otherAttr='pt-br foo bar' /> */ -/* Você pode direciona-lo usando uma das suas classes CSS */ +/* Você pode direcioná-lo usando uma das suas classes CSS */ .class1 { } /* ou ambas as classes! */ @@ -80,9 +82,9 @@ classe div.some [attr $ = 'ue'] {} /* Você pode selecionar um elemento que é filho de outro elemento */ div.some-parent> .class-name {} -/* Ou um descendente de um outro elemento. As crianças são os descendentes diretos de - seu elemento pai, apenas um nível abaixo da árvore. Pode ser qualquer descendentes - nivelar por baixo da árvore. */ +/* Ou um descendente de um outro elemento. Os filhos são os descendentes diretos de + seu elemento pai, apenas um nível abaixo da árvore. Pode ser quaisquer descendentes + nivelados por baixo da árvore. */ div.some-parent class-name {} /* Atenção: o mesmo seletor sem espaço tem um outro significado. @@ -95,7 +97,7 @@ div.some-parent.class-name {} /* Ou qualquer irmão que o precede */ .i am-qualquer-elemento antes ~ .Este elemento {} -/* Existem alguns selectores chamado pseudo classes que podem ser usados para selecionar um +/* Existem alguns seletores chamados pseudo classes que podem ser usados para selecionar um elemento quando ele está em um determinado estado */ /* Por exemplo, quando o cursor passa sobre um elemento */ @@ -116,7 +118,7 @@ seletor:first-child {} /* Qualquer elemento que é o último filho de seu pai */ seletor:last-child {} -/* Assim como pseudo classes, pseudo elementos permitem que você estilo certas partes de um documento */ +/* Assim como pseudo classes, pseudo elementos permitem que você estilize certas partes de um documento */ /* Corresponde a um primeiro filho virtual do elemento selecionado */ seletor::before {} @@ -125,10 +127,10 @@ seletor::before {} seletor::after {} /* Nos locais apropriados, um asterisco pode ser utilizado como um curinga para selecionar todos - elemento */ + os elementos */ * {} /* */ Todos os elementos .parent * {} /* */ todos os descendentes -.parent> * {} /* */ todas as crianças +.parent> * {} /* */ todos os filhos /* #################### ## PROPRIEDADES @@ -139,7 +141,7 @@ seletor { /* Unidades de comprimento pode ser absoluta ou relativa. */ /* Unidades relativas */ - width: 50%; /* Percentagem de largura elemento pai */ + width: 50%; /* Percentagem de largura do elemento pai */ font-size: 2em; /* Múltiplos de font-size original de elemento */ font-size: 2rem; /* Ou do elemento raiz font-size */ font-size: 2vw; /* Múltiplos de 1% da largura da janela de exibição (CSS 3) */ @@ -179,7 +181,7 @@ seletor { ## Uso -Guardar uma folha de estilo CSS com a extensão `.css`. +Salvar uma folha de estilo CSS com a extensão `.css`. ```xml <!-- Você precisa incluir o arquivo css no da sua página <head>. Isto é o @@ -198,7 +200,7 @@ Guardar uma folha de estilo CSS com a extensão `.css`. ## Precedência ou Cascata -Um elemento pode ser alvo de vários seletores e pode ter um conjunto de propriedades em que mais de uma vez. Nestes casos, uma das regras tem precedência sobre os outros. Geralmente, uma regra em um seletor mais específico têm precedência sobre um menos específico, e uma regra que ocorre mais tarde na folha de estilo substitui uma anterior. +Um elemento pode ser alvo de vários seletores e pode ter um conjunto de propriedades em que mais de uma vez. Nestes casos, uma das regras tem precedência sobre as outras. Geralmente, uma regra em um seletor mais específico têm precedência sobre um menos específico, e uma regra que ocorre mais tarde na folha de estilo substitui uma anterior. Este processo é chamado de cascata, portanto, as Fichas de nome de estilo em cascata. @@ -236,9 +238,48 @@ A precedência de estilo é a seguinte. Lembre-se, a precedência é para cada * `B` é o próximo. * `D` é a última. +## Media Queries +Media queries são recursos do CSS3 que permitem especificar quando determinadas regras de CSS devem ser aplicadas; é possível aplicar regras diferentes quando a página é impressa, quando a tela possui determinadas dimensões ou densidade de pixels e quando é lida por um leitor de tela. Media queries não adicionam especificidade ao seletor. + +```css +/* Uma regra que será aplicada a todos os dispositivos */ +h1 { + font-size: 2em; + color: white; + background-color: black; +} + +/* Altera a cor do h1 para utilizar menos tinta durante a impressão */ +@media print { + h1 { + color: black; + background-color: white; + } +} + +/* Altera o tamanho da fonte quando exibida numa tela com pelo menos 480px de largura */ +@media screen and (min-width: 480px) { + h1 { + font-size: 3em; + font-weight: normal; + } +} +``` +Media queries podem incluir os seguintes atributos: `width`, `height`, `device-width`, `device-height`, `orientation`, `aspect-ratio`, `device-aspect-ratio`, `color`, `color-index`, `monochrome`, `resolution`, `scan`, `grid`. A maioria desses atributos pode ser prefixada com `min-` ou `max-`. + +O atributo `resolution` não é suportado em dispositivos mais antigos. Em vez disso, use `device-pixel-ratio`. + +Muitos smartphones e tablets tentarão renderizar a página como se estivesse num desktop a menos que você utilize a meta-tag `viewport`. + +```html +<head> + <meta name="viewport" content="width=device-width; initial-scale=1.0"> +</head> +``` + ## Compatibilidade -A maior parte dos recursos do CSS 2 (e muitos em CSS 3) estão disponíveis em todos os navegadores e dispositivos. Mas é sempre boa prática para verificar antes de usar um novo recurso. +A maior parte dos recursos do CSS 2 (e muitos em CSS 3) estão disponíveis em todos os navegadores e dispositivos. Mas é sempre boa prática verificar antes de usar um novo recurso. ## Recursos diff --git a/pt-br/cypher-pt.html.markdown b/pt-br/cypher-pt.html.markdown new file mode 100644 index 00000000..d4400148 --- /dev/null +++ b/pt-br/cypher-pt.html.markdown @@ -0,0 +1,250 @@ +--- +language: cypher +filename: LearnCypher-br.cql +contributors: + - ["Théo Gauchoux", "https://github.com/TheoGauchoux"] + +lang: pt-br +--- + +O Cypher é a linguagem de consulta do Neo4j para manipular gráficos facilmente. Ela reutiliza a sintaxe do SQL e a mistura com o tipo de ascii-art para representar gráficos. Este tutorial pressupõe que você já conheça conceitos de gráficos como nós e relacionamentos. + +[Leia mais aqui.](https://neo4j.com/developer/cypher-query-language/) + + +Nós +--- + +**Representa um registro em um gráfico.** + +`()` +É um *nó* vazio, para indicar que existe um *nó*, mas não é relevante para a consulta. + +`(n)` +É um *nó* referido pela variável **n**, reutilizável na consulta. Começa com minúsculas e usa o camelCase. + +`(p:Person)` +Você pode adicionar um *label* ao seu nó, aqui **Person**. É como um tipo / uma classe / uma categoria. Começa com maiúsculas e usa o camelCase. + +`(p:Person:Manager)` +Um nó pode ter muitos *labels*. + +`(p:Person {name : 'Théo Gauchoux', age : 22})` +Um nó pode ter algumas *propriedades*, aqui **name** e **age**. Começa com minúsculas e usa o camelCase. + +Os tipos permitidos nas propriedades: + + - Numeric + - Boolean + - String + - Lista de tipos primitivos anteriores + +*Aviso: não há propriedade datetime no Cypher! Você pode usar String com um padrão específico ou um Numeric a partir de uma data específica.* + +`p.name` +Você pode acessar uma propriedade com o estilo de ponto. + + +Relacionamentos (ou Arestas) +--- + +**Conecta dois nós** + +`[:KNOWS]` +É um *relacionamento* com o *label* **KNOWS**. É um *label* como um rótulo do nó. Começa com maiúsculas e usa UPPER_SNAKE_CASE. + +`[k:KNOWS]` +O mesmo *relacionamento*, referido pela variável **k**, reutilizável na consulta, mas não é necessário. + +`[k:KNOWS {since:2017}]` +O mesmo *relacionamento*, com *propriedades* (como *nó*), aqui **since**. + +`[k:KNOWS*..4]` +É uma informação estrutural para usar em um *path* (visto posteriormente). Aqui, **\*..4** diz, “Corresponda o padrão, com a relação **k** que é repetida de 1 a 4 vezes. + + +Paths +--- + +**A maneira de misturar nós e relacionamentos.** + +`(a:Person)-[:KNOWS]-(b:Person)` +Um path descrevendo que **a** e **b** se conhecem. + +`(a:Person)-[:MANAGES]->(b:Person)` +Um path pode ser direcionado. Este path descreve que **a** é o gerente de **b**. + +`(a:Person)-[:KNOWS]-(b:Person)-[:KNOWS]-(c:Person)` +Você pode encadear vários relacionamentos. Este path descreve o amigo de um amigo. + +`(a:Person)-[:MANAGES]->(b:Person)-[:MANAGES]->(c:Person)` +Uma encadeamento também pode ser direcionada. Este path descreve que **a** é o chefe de **b** e o grande chefe de **c**. + +Padrões frequentemente usados (do Neo4j doc) : + +``` +// Amigo de um amigo +(user)-[:KNOWS]-(friend)-[:KNOWS]-(foaf) + +// Path mais curto +path = shortestPath( (user)-[:KNOWS*..5]-(other) ) + +// Filtragem colaborativa +(user)-[:PURCHASED]->(product)<-[:PURCHASED]-()-[:PURCHASED]->(otherProduct) + +// Navegação de árvore +(root)<-[:PARENT*]-(leaf:Category)-[:ITEM]->(data:Product) + +``` + + +Crie consultas +--- + +Crie um novo nó +``` +CREATE (a:Person {name:"Théo Gauchoux"}) +RETURN a +``` +*`RETURN` permite ter um resultado após a consulta. Pode ser múltiplo, como `RETURN a, b`.* + +Crie um novo relacionamento (com 2 novos nós) +``` +CREATE (a:Person)-[k:KNOWS]-(b:Person) +RETURN a,k,b +``` + +Consultas que casam +--- + +Casam todos os nós +``` +MATCH (n) +RETURN n +``` + +Casam nós por label +``` +MATCH (a:Person) +RETURN a +``` + +Casam nós por label e propriedade +``` +MATCH (a:Person {name:"Théo Gauchoux"}) +RETURN a +``` + +Casam nós de acordo com os relacionamentos (não direcionados) +``` +MATCH (a)-[:KNOWS]-(b) +RETURN a,b +``` + +Casam nós de acordo com os relacionamentos (direcionados) +``` +MATCH (a)-[:MANAGES]->(b) +RETURN a,b +``` + +Casam nós com um cláusula `WHERE` +``` +MATCH (p:Person {name:"Théo Gauchoux"})-[s:LIVES_IN]->(city:City) +WHERE s.since = 2015 +RETURN p,state +``` + +Você pode usa a cláusula `MATCH WHERE` com a cláusula `CREATE` +``` +MATCH (a), (b) +WHERE a.name = "Jacquie" AND b.name = "Michel" +CREATE (a)-[:KNOWS]-(b) +``` + + +Atualizar consultas +--- + +Atualizar uma propriedade específica de um nó +``` +MATCH (p:Person) +WHERE p.name = "Théo Gauchoux" +SET p.age = 23 +``` + +Substituir todas as propriedades de um nó +``` +MATCH (p:Person) +WHERE p.name = "Théo Gauchoux" +SET p = {name: "Michel", age: 23} +``` + +Adicionar nova propriedade a um nó +``` +MATCH (p:Person) +WHERE p.name = "Théo Gauchoux" +SET p + = {studies: "IT Engineering"} +``` + +Adicione um label a um nó +``` +MATCH (p:Person) +WHERE p.name = "Théo Gauchoux" +SET p:Internship +``` + + +Excluir consultas +--- + +Excluir um nó específico (os relacionamentos vinculados devem ser excluídos antes) +``` +MATCH (p:Person)-[relationship]-() +WHERE p.name = "Théo Gauchoux" +DELETE relationship, p +``` + +Remover uma propriedade em um nó específico +``` +MATCH (p:Person) +WHERE p.name = "Théo Gauchoux" +REMOVE p.age +``` +*Prestar atenção à palavra chave `REMOVE`, não é `DELETE` !* + +Remover um label de um nó específico +``` +MATCH (p:Person) +WHERE p.name = "Théo Gauchoux" +DELETE p:Person +``` + +Excluir o banco de dados inteiro +``` +MATCH (n) +OPTIONAL MATCH (n)-[r]-() +DELETE n, r +``` +*Sério, é o `rm -rf /` do Cypher !* + + +Outras cláusulas úteis +--- + +`PROFILE` +Antes de uma consulta, mostre o plano de execução dela. + +`COUNT(e)` +Contar entidades (nós ou relacionamentos) que casam com **e**. + +`LIMIT x` +Limite o resultado aos primeiros x resultados. + + +Dicas Especiais +--- + +- Há apenas comentários de uma linha no Cypher, com barras duplas : // Comentários +- Você pode executar um script Cypher armazenado em um arquivo **.cql** diretamente no Neo4j (é uma importação). No entanto, você não pode ter várias instruções neste arquivo (separadas por **;**). +- Use o shell Neo4j para escrever Cypher, é realmente incrível. +- O Cypher será a linguagem de consulta padrão para todos os bancos de dados de gráficos (conhecidos como **OpenCypher**). diff --git a/pt-br/dart-pt.html.markdown b/pt-br/dart-pt.html.markdown new file mode 100644 index 00000000..e9d72850 --- /dev/null +++ b/pt-br/dart-pt.html.markdown @@ -0,0 +1,509 @@ +--- +language: dart +filename: learndart-pt.dart +contributors: + - ["Joao Pedrosa", "https://github.com/jpedrosa/"] +translators: + - ["Junior Damacena", "https://github.com/jdamacena/"] +lang: pt-br +--- + +Dart é uma novata no reino das linguagens de programação. +Ela empresta muito de outras linguagens mais conhecidas, e tem a meta de não se diferenciar muito de seu irmão, JavaScript. Assim como JavaScript, Dart foi pensada para oferecer grande integração com o Browser. + +A característica mais controversa da Dart é a sua Tipagem Opcional, ou seja, não é obrigatório declarar tipos. + +```dart +import "dart:collection"; +import "dart:math" as DM; + +// Bem vindo ao Aprenda Dart em 15 minutos. http://www.dartlang.org/ +// Este é um tutorial executável. Você pode rodar esse tutorial com Dart ou no +// site Try Dart!, é só copiar e colar este código lá. http://try.dartlang.org/ + +// Declarações de funções e métodos são iguais. Declarações de funções +// podem ser aninhadas. A declaração é feita das seguintes formas +// nome() {} ou nome() => expressaoDeUmaLinhaSo; +// A declaração feita com a seta tem um return implícito para o resultado da +// expressão. +example1() { + example1nested1() { + example1nested2() => print("Example1 nested 1 nested 2"); + example1nested2(); + } + example1nested1(); +} + +// Funções anônimas são criadas sem um nome. +example2() { + example2nested1(fn) { + fn(); + } + example2nested1(() => print("Example2 nested 1")); +} + +// Quando uma função é declarada como parâmetro, a declaração pode incluir o número +// de parâmetros que a função recebe, isso é feito especificando o nome de cada um dos +// parâmetros que serão recebidos pela função. +example3() { + example3nested1(fn(informSomething)) { + fn("Example3 nested 1"); + } + example3planB(fn) { // Ou não declare o número de parâmetros. + fn("Example3 plan B"); + } + example3nested1((s) => print(s)); + example3planB((s) => print(s)); +} + +// Funções têm acesso à variáveis fora de seu escopo +var example4Something = "Example4 nested 1"; +example4() { + example4nested1(fn(informSomething)) { + fn(example4Something); + } + example4nested1((s) => print(s)); +} + +// Declaração de classe com um método chamado sayIt, que também tem acesso +// à variável externa, como se fosse uma função como se viu antes. +var example5method = "Example5 sayIt"; +class Example5Class { + sayIt() { + print(example5method); + } +} +example5() { + // Criar uma instância anônima de Example5Class e chamar o método sayIt + // nela. + new Example5Class().sayIt(); +} + +// A declaração de uma classe é feita da seguinte maneira: class name { [classBody] }. +// onde classBody pode incluir métodos e variáveis de instância, assim como +// métodos e variáveis de classe. +class Example6Class { + var example6InstanceVariable = "Example6 instance variable"; + sayIt() { + print(example6InstanceVariable); + } +} +example6() { + new Example6Class().sayIt(); +} + +// Métodos e variáveis de classe são declarados como "static". +class Example7Class { + static var example7ClassVariable = "Example7 class variable"; + static sayItFromClass() { + print(example7ClassVariable); + } + sayItFromInstance() { + print(example7ClassVariable); + } +} +example7() { + Example7Class.sayItFromClass(); + new Example7Class().sayItFromInstance(); +} + +// Literais são ótimos, mas há uma limitação para o que eles podem ser +// quando estão fora do corpo de uma função/método. Literais fora do escopo da classe +// ou fora da classe têm que ser constantes. Strings e números são constantes +// por padrão. Mas arrays e mapas não. Eles podem ser declarados como constantes +// usando o comando "const". +var example8A = const ["Example8 const array"], + example8M = const {"someKey": "Example8 const map"}; +example8() { + print(example8A[0]); + print(example8M["someKey"]); +} + +// Loops em Dart são criados com for () {} ou while () {}, +// um pouco mais moderno temos for (.. in ..) {}, ou funções de callbacks com muitas +// funcionalidades, começando com o forEach. +var example9A = const ["a", "b"]; +example9() { + for (var i = 0; i < example9A.length; i++) { + print("Example9 for loop '${example9A[i]}'"); + } + var i = 0; + while (i < example9A.length) { + print("Example9 while loop '${example9A[i]}'"); + i++; + } + for (var e in example9A) { + print("Example9 for-in loop '${e}'"); + } + example9A.forEach((e) => print("Example9 forEach loop '${e}'")); +} + +// Para percorrer os caracteres de uma string ou extrair uma substring. +var example10S = "ab"; +example10() { + for (var i = 0; i < example10S.length; i++) { + print("Example10 String character loop '${example10S[i]}'"); + } + for (var i = 0; i < example10S.length; i++) { + print("Example10 substring loop '${example10S.substring(i, i + 1)}'"); + } +} + +// Int e double são os dois formatos de número suportados. +example11() { + var i = 1 + 320, d = 3.2 + 0.01; + print("Example11 int ${i}"); + print("Example11 double ${d}"); +} + +// DateTime traz operações com data/hora. +example12() { + var now = new DateTime.now(); + print("Example12 now '${now}'"); + now = now.add(new Duration(days: 1)); + print("Example12 tomorrow '${now}'"); +} + +// Expressões regulares são suportadas. +example13() { + var s1 = "some string", s2 = "some", re = new RegExp("^s.+?g\$"); + match(s) { + if (re.hasMatch(s)) { + print("Example13 regexp matches '${s}'"); + } else { + print("Example13 regexp doesn't match '${s}'"); + } + } + match(s1); + match(s2); +} + +// Expressões booleanas precisam retornar ou true ou false, já que +// Dart não faz a conversão implicitamente. +example14() { + var v = true; + if (v) { + print("Example14 value is true"); + } + v = null; + try { + if (v) { + // Nunca seria executada + } else { + // Nunca seria executada + } + } catch (e) { + print("Example14 null value causes an exception: '${e}'"); + } +} + +// try/catch/finally e throw são usados para tratamento de exceções. +// throw aceita qualquer objeto como parâmetro; +example15() { + try { + try { + throw "Some unexpected error."; + } catch (e) { + print("Example15 an exception: '${e}'"); + throw e; // Re-throw + } + } catch (e) { + print("Example15 catch exception being re-thrown: '${e}'"); + } finally { + print("Example15 Still run finally"); + } +} + +// Para mais eficiência ao criar strings longas dinamicamente, use o +// StringBuffer. Ou você pode também concatenar um array de strings. +example16() { + var sb = new StringBuffer(), a = ["a", "b", "c", "d"], e; + for (e in a) { sb.write(e); } + print("Example16 dynamic string created with " + "StringBuffer '${sb.toString()}'"); + print("Example16 join string array '${a.join()}'"); +} + +// Strings podem ser concatenadas apenas colocando strings literais uma perto +// da outra, sem necessidade de nenhum outro operador. +example17() { + print("Example17 " + "concatenar " + "strings " + "é simples assim"); +} + +// Strings podem ser delimitadas por apóstrofos ou aspas e não há +// diferença entre os dois. Essa flexibilidade pode ser boa para +// evitar a necessidade de escapar conteúdos que contenham o delimitador da string. +// Por exemplo, aspas dos atributos HTMLse a string conter HTML. +example18() { + print('Example18 <a href="etc">' + "Don't can't I'm Etc" + '</a>'); +} + +// Strings com três apóstrofos ou aspas podem +// ter muitas linhas e incluem os delimitadores de linha (ou seja, os enter). +example19() { + print('''Example19 <a href="etc"> +Example19 Don't can't I'm Etc +Example19 </a>'''); +} + +// Strings têm a função de interpolação que é chamada com o caractere $. +// Com $ { [expression] }, o retorno da expressão é interpolado. +// $ seguido pelo nome de uma variável interpola o conteúdo dessa variável. +// $ pode ser escapedo assim \$. +example20() { + var s1 = "'\${s}'", s2 = "'\$s'"; + print("Example20 \$ interpolation ${s1} or $s2 works."); +} + +// A tipagem opcional permite que APIs usem anotações e também ajuda os +// IDEs na hora das refatorações, auto-complete e checagem de +// erros. Note que até agora não declaramos nenhum tipo e o programa está +// funcionando normalmente. De fato, os tipos são ignorados em tempo de execução. +// Os tipos podem até mesmo estarem errados e o programa ainda vai dar o +// benefício da dúvida e rodar, visto que os tipos não importam. +// Existe um parâmetro que checa erros de tipagem que é o +// checked mode, dizem que é útil enquanto se está desenvolvendo, +// mas também é mais lento devido às checagens extras e por isso +// é evitado em ambiente de produção. +class Example21 { + List<String> _names; + Example21() { + _names = ["a", "b"]; + } + List<String> get names => _names; + set names(List<String> list) { + _names = list; + } + int get length => _names.length; + void add(String name) { + _names.add(name); + } +} +void example21() { + Example21 o = new Example21(); + o.add("c"); + print("Example21 names '${o.names}' and length '${o.length}'"); + o.names = ["d", "e"]; + print("Example21 names '${o.names}' and length '${o.length}'"); +} + +// Herança em classes é feito assim: class name extends AnotherClassName {}. +class Example22A { + var _name = "Some Name!"; + get name => _name; +} +class Example22B extends Example22A {} +example22() { + var o = new Example22B(); + print("Example22 class inheritance '${o.name}'"); +} + +// Mistura de classes também é possível, e é feito assim: +// class name extends SomeClass with AnotherClassName {} +// É necessário extender uma classe para poder misturar com outra. +// No momento, classes misturadas não podem ter construtor. +// Mistura de classes é mais usado para compartilhar métodos com classes distantes, então +// a herança comum não fica no caminho do reuso de código. +// As misturas aparecem após o comando "with" na declaração da classe. +class Example23A {} +class Example23Utils { + addTwo(n1, n2) { + return n1 + n2; + } +} +class Example23B extends Example23A with Example23Utils { + addThree(n1, n2, n3) { + return addTwo(n1, n2) + n3; + } +} +example23() { + var o = new Example23B(), r1 = o.addThree(1, 2, 3), + r2 = o.addTwo(1, 2); + print("Example23 addThree(1, 2, 3) results in '${r1}'"); + print("Example23 addTwo(1, 2) results in '${r2}'"); +} + +// O método construtor da classe usa o mesmo nome da classe e +// é feito assim SomeClass() : super() {}, onde a parte ": super()" +// é opcional e é usada para passar parâmetros estáticos para o +// construtor da classe pai. +class Example24A { + var _value; + Example24A({value: "someValue"}) { + _value = value; + } + get value => _value; +} +class Example24B extends Example24A { + Example24B({value: "someOtherValue"}) : super(value: value); +} +example24() { + var o1 = new Example24B(), + o2 = new Example24B(value: "evenMore"); + print("Example24 calling super during constructor '${o1.value}'"); + print("Example24 calling super during constructor '${o2.value}'"); +} + +// Há um atalho para passar parâmetros para o construtor no caso de classes mais simples. +// Simplesmente use o prefixo this.nomeDoParametro e isso irá passar o parâmetro para uma +// instância de variável de mesmo nome. +class Example25 { + var value, anotherValue; + Example25({this.value, this.anotherValue}); +} +example25() { + var o = new Example25(value: "a", anotherValue: "b"); + print("Example25 shortcut for constructor '${o.value}' and " + "'${o.anotherValue}'"); +} + +// Parâmetros com nome estão disponíveis quando declarados entre {}. +// Quando os parâmetros têm nomes, eles podem ser passados em qualquer ordem. +// Parâmetros declarados entre [] são opcionais. +example26() { + var _name, _surname, _email; + setConfig1({name, surname}) { + _name = name; + _surname = surname; + } + setConfig2(name, [surname, email]) { + _name = name; + _surname = surname; + _email = email; + } + setConfig1(surname: "Doe", name: "John"); + print("Example26 name '${_name}', surname '${_surname}', " + "email '${_email}'"); + setConfig2("Mary", "Jane"); + print("Example26 name '${_name}', surname '${_surname}', " + "email '${_email}'"); +} + +// Variáveis declaradas com um final só podem receber valor uma vez. +// No caso de classes, variáveis final podem ter valor atribuido através +// de um parâmetro no construtor +class Example27 { + final color1, color2; + // Um pouco de flexibilidade ao criar variáveis final com a sintaxe + // que é a seguinte: + Example27({this.color1, color2}) : color2 = color2; +} +example27() { + final color = "orange", o = new Example27(color1: "lilac", color2: "white"); + print("Example27 color is '${color}'"); + print("Example27 color is '${o.color1}' and '${o.color2}'"); +} + +// para importar uma biblioteca, use import "libraryPath" ou se for uma biblioteca da linguagem, +// import "dart:libraryName". Também tem o gerenciador de pacotes "pub"que tem +// sua própria convenção de import "package:packageName". +// Veja o import "dart:collection"; no início do arquivo. Imports devem vir no início +// do arquivo. IterableBase vem de dart:collection. +class Example28 extends IterableBase { + var names; + Example28() { + names = ["a", "b"]; + } + get iterator => names.iterator; +} +example28() { + var o = new Example28(); + o.forEach((name) => print("Example28 '${name}'")); +} + +// Para controle de fluxo nós temos: +// * switch com comandos break obrigatórios +// * if-else if-else e se-ternário ..?..:.. +// * closures e funções anônimas +// * comandos break, continue e return +example29() { + var v = true ? 30 : 60; + switch (v) { + case 30: + print("Example29 switch statement"); + break; + } + if (v < 30) { + } else if (v > 30) { + } else { + print("Example29 if-else statement"); + } + callItForMe(fn()) { + return fn(); + } + rand() { + v = new DM.Random().nextInt(50); + return v; + } + while (true) { + print("Example29 callItForMe(rand) '${callItForMe(rand)}'"); + if (v != 30) { + break; + } else { + continue; + } + // Nunca chega aqui. + } +} + +// Você pode converter string para int, double para int, ou só pegar a parte inteira da divisão +// usando o comando ~/. Vamos jogar um jogo de adivinhação. +example30() { + var gn, tooHigh = false, + n, n2 = (2.0).toInt(), top = int.parse("123") ~/ n2, bottom = 0; + top = top ~/ 6; + gn = new DM.Random().nextInt(top + 1); // +1 porque o máximo do nextInt conta o número passado - 1 + print("Example30 Diga um número entre 0 e ${top}"); + guessNumber(i) { + if (n == gn) { + print("Example30 Você acertou! O número é ${gn}"); + } else { + tooHigh = n > gn; + print("Example30 O número ${n} é muito " + "${tooHigh ? 'alto' : 'baixo'}. Tente de novo"); + } + return n == gn; + } + n = (top - bottom) ~/ 2; + while (!guessNumber(n)) { + if (tooHigh) { + top = n - 1; + } else { + bottom = n + 1; + } + n = bottom + ((top - bottom) ~/ 2); + } +} + +// Programas em Dart só têm um ponto de entrada, que é a função main. +// Nada será executado antes da funcão main de um programa. +// Isso ajuda a carregar o programa mais rapidamente, até mesmo quando o +// carregamento é "Lazy". +// O programa deve começar com: +main() { + print("Aprenda Dart em 15 minutos!"); + [example1, example2, example3, example4, example5, example6, example7, + example8, example9, example10, example11, example12, example13, example14, + example15, example16, example17, example18, example19, example20, + example21, example22, example23, example24, example25, example26, + example27, example28, example29, example30 + ].forEach((ef) => ef()); +} + +``` + +## Continue lendo + +Dart tem um site bastante fácil de entender. Ele tem os docs da API, tutoriais, artigos e muito mais, incluindo uma +opção muito útil de testar o Dart online. +* [https://www.dartlang.org](https://www.dartlang.org) +* [https://try.dartlang.org](https://try.dartlang.org) + + + + diff --git a/pt-br/dynamic-programming-pt.html.markdown b/pt-br/dynamic-programming-pt.html.markdown index 8de9bee6..93171955 100644 --- a/pt-br/dynamic-programming-pt.html.markdown +++ b/pt-br/dynamic-programming-pt.html.markdown @@ -22,16 +22,16 @@ Sempre se lembre!! ## Maneiras de Solucionar tais Problemas -1. Top-Down (De cima para baixo): Começe solucionando o problema quebrando-o em +1. Top-Down (De cima para baixo): Comece solucionando o problema quebrando-o em partes. Se você perceber que o problema já foi resolvido, então simplemente pegue a resposta salva. Se ainda não foi resolvido, solucione-o e salve a resposta. Isso é geralmente fácil de pensar e muito intuitivo. É geralmente referenciado como Memorização. 2. Bottom-Up (De baixo para cima): Analise o problema e veja a ordem em que os -subproblemas são resolvidos e começe a solucionar dos problemas mais triviais, +subproblemas são resolvidos e comece a solucionar dos problemas mais triviais, até o problema dado. Neste processo, é garantido que os subproblemas são -resolvidos antes de resoler o problema. Isto é referenciado como Programação Dinâmica. +resolvidos antes de resolver o problema. Isto é referenciado como Programação Dinâmica. ## Exemplo de Programação Dinâmica @@ -51,7 +51,7 @@ array antecedente e uma variável como maiorSequenciasAteAgora e seu índice ajudariam a poupar muito tempo. Um conceito similar poderia ser aplicado ao procurar o maior caminho em um grafo acíclico dirigido. ---------------------------------------------------------------------------- + ``` for i=0 to n-1 LS[i]=1 @@ -62,14 +62,12 @@ grafo acíclico dirigido. if (largest < LS[i]) ``` -### Alguns Problemas Famosos de Programação Dinâmica -``` -Floyd Warshall Algorithm - Tutorial and C Program source code:http://www.thelearningpoint.net/computer-science/algorithms-all-to-all-shortest-paths-in-graphs---floyd-warshall-algorithm-with-c-program-source-code - -Integer Knapsack Problem - Tutorial and C Program source code: http://www.thelearningpoint.net/computer-science/algorithms-dynamic-programming---the-integer-knapsack-problem +## Alguns Problemas Famosos de Programação Dinâmica -Longest Common Subsequence - Tutorial and C Program source code : http://www.thelearningpoint.net/computer-science/algorithms-dynamic-programming---longest-common-subsequence -``` +- [Floyd Warshall Algorithm - Tutorial and C Program source code](http://www.thelearningpoint.net/computer-science/algorithms-all-to-all-shortest-paths-in-graphs---floyd-warshall-algorithm-with-c-program-source-code) +- [Integer Knapsack Problem - Tutorial and C Program source code](http://www.thelearningpoint.net/computer-science/algorithms-dynamic-programming---the-integer-knapsack-problem) +- [Longest Common Subsequence - Tutorial and C Program source code](http://www.thelearningpoint.net/computer-science/algorithms-dynamic-programming---longest-common-subsequence) + ## Recursos Online (EN) diff --git a/pt-br/elisp-pt.html.markdown b/pt-br/elisp-pt.html.markdown index fc2d1e40..aa611097 100644 --- a/pt-br/elisp-pt.html.markdown +++ b/pt-br/elisp-pt.html.markdown @@ -111,7 +111,7 @@ filename: learn-emacs-lisp-pt.el (hello) ;; `C-xC-e' => Hello, I am Bastien -;; Os parêntesis vazios na definição da função significam que ela +;; Os parênteses vazios na definição da função significam que ela ;; não aceita argumentos. Mas sempre utilizar `my-name' é um tédio! ;; Vamos dizer à função para aceitar um argumento (o argumento é ;; chamado "name"): diff --git a/pt-br/elixir.html.markdown b/pt-br/elixir-pt.html.markdown index f8c56101..4ba78f52 100644 --- a/pt-br/elixir.html.markdown +++ b/pt-br/elixir-pt.html.markdown @@ -40,7 +40,7 @@ e muitos outros recursos. # Tuplas que são guardadas contiguamente em memória. {1,2,3} # tupla -# Podemos acessar um elemento de uma tupla om a função `elem`: +# Podemos acessar um elemento de uma tupla com a função `elem`: elem({1, 2, 3}, 0) #=> 1 # Listas que são implementadas como listas ligadas. diff --git a/pt-br/elm-pt.html.markdown b/pt-br/elm-pt.html.markdown index 78a4f1b7..d2469a93 100644 --- a/pt-br/elm-pt.html.markdown +++ b/pt-br/elm-pt.html.markdown @@ -76,8 +76,8 @@ List.head [] -- Nothing -- Acesse os elementos de um par com as funções first e second. -- (Este é um atalho; nós iremos para o "caminho real" em breve.) -fst ("elm", 42) -- "elm" -snd ("elm", 42) -- 42 +Tuple.first ("elm", 42) -- "elm" +Tuple.second ("elm", 42) -- 42 -- Uma tupla vazia ou "unidade" às vezes é utilizada como um placeholder. -- É o único valor de seu tipo, também chamado de "Unit". diff --git a/pt-br/factor-pt.html.markdown b/pt-br/factor-pt.html.markdown new file mode 100644 index 00000000..b4b5c7f5 --- /dev/null +++ b/pt-br/factor-pt.html.markdown @@ -0,0 +1,184 @@ +--- +language: factor +contributors: + - ["hyphz", "http://github.com/hyphz/"] +filename: learnfactor-br.factor + +lang: pt-br +--- + +Factor é uma linguagem moderna baseada em pilha, baseado em Forth, criada por Slava Pestov. + +Código neste arquivo pode ser digitado em Fator, mas não importado diretamente porque o cabeçalho de vocabulário e importação faria o início completamente confuso. + +```factor +! Este é um comentário + +! Como Forth, toda a programação é feita manipulando a pilha. +! A indicação de um valor literal o coloca na pilha. +5 2 3 56 76 23 65 ! Nenhuma saída, mas a pilha é impressa no modo interativo + +! Esses números são adicionados à pilha, da esquerda para a direita. +! .s imprime a pilha de forma não destrutiva. +.s ! 5 2 3 56 76 23 65 + +! A aritmética funciona manipulando dados na pilha. +5 4 + ! Sem saída + +! `.` mostra o resultado superior da pilha e o imprime. +. ! 9 + +! Mais exemplos de aritmética: +6 7 * . ! 42 +1360 23 - . ! 1337 +12 12 / . ! 1 +13 2 mod . ! 1 + +99 neg . ! -99 +-99 abs . ! 99 +52 23 max . ! 52 +52 23 min . ! 23 + +! Várias palavras são fornecidas para manipular a pilha, coletivamente conhecidas como palavras embaralhadas. + +3 dup - ! duplica o primeiro item (1st agora igual a 2nd): 3 - 3 +2 5 swap / ! troca o primeiro com o segundo elemento: 5 / 2 +4 0 drop 2 / ! remove o primeiro item (não imprima na tela): 4 / 2 +1 2 3 nip .s ! remove o segundo item (semelhante a drop): 1 3 +1 2 clear .s ! acaba com toda a pilha +1 2 3 4 over .s ! duplica o segundo item para o topo: 1 2 3 4 3 +1 2 3 4 2 pick .s ! duplica o terceiro item para o topo: 1 2 3 4 2 3 + +! Criando Palavras +! O `:` conjuntos de palavras do Factor no modo de compilação até que ela veja a palavra `;`. +: square ( n -- n ) dup * ; ! Sem saída +5 square . ! 25 + +! Podemos ver o que as palavra fazem também. +! \ suprime a avaliação de uma palavra e coloca seu identificador na pilha. +\ square see ! : square ( n -- n ) dup * ; + +! Após o nome da palavra para criar, a declaração entre parênteses dá o efeito da pilha. +! Podemos usar os nomes que quisermos dentro da declaração: +: weirdsquare ( camel -- llama ) dup * ; + +! Contanto que sua contagem corresponda ao efeito da pilha da palavra: +: doubledup ( a -- b ) dup dup ; ! Error: Stack effect declaration is wrong +: doubledup ( a -- a a a ) dup dup ; ! Ok +: weirddoubledup ( i -- am a fish ) dup dup ; ! Além disso Ok + +! Onde Factor difere do Forth é no uso de citações. +! Uma citação é um bloco de código que é colocado na pilha como um valor. +! [ inicia o modo de citação; ] termina. +[ 2 + ] ! A citação que adiciona 2 é deixada na pilha +4 swap call . ! 6 + +! E assim, palavras de ordem mais alta. TONS de palavras de ordem superior. +2 3 [ 2 + ] dip .s ! Retira valor do topo da pilha, execute citação, empurre de volta: 4 3 +3 4 [ + ] keep .s ! Copie o valor do topo da pilha, execute a citação, envie a cópia: 7 4 +1 [ 2 + ] [ 3 + ] bi .s ! Executar cada citação no valor do topo, empurrar os dois resultados: 3 4 +4 3 1 [ + ] [ + ] bi .s ! As citações em um bi podem extrair valores mais profundos da pilha: 4 5 ( 1+3 1+4 ) +1 2 [ 2 + ] bi@ .s ! Executar a citação no primeiro e segundo valores +2 [ + ] curry ! Injeta o valor fornecido no início da citação: [ 2 + ] é deixado na pilha + +! Condicionais +! Qualquer valor é verdadeiro, exceto o valor interno f. +! m valor interno não existe, mas seu uso não é essencial. +! Condicionais são palavras de maior ordem, como com os combinadores acima. + +5 [ "Five is true" . ] when ! Cinco é verdadeiro +0 [ "Zero is true" . ] when ! Zero é verdadeiro +f [ "F is true" . ] when ! Sem saída +f [ "F is false" . ] unless ! F é falso +2 [ "Two is true" . ] [ "Two is false" . ] if ! Two é verdadeiro + +! Por padrão, as condicionais consomem o valor em teste, mas variantes com asterisco +! deixe sozinho se é verdadeiro: + +5 [ . ] when* ! 5 +f [ . ] when* ! Nenhuma saída, pilha vazia, f é consumida porque é falsa + + +! Laços +! Você adivinhou .. estas são palavras de ordem mais elevada também. + +5 [ . ] each-integer ! 0 1 2 3 4 +4 3 2 1 0 5 [ + . ] each-integer ! 0 2 4 6 8 +5 [ "Hello" . ] times ! Hello Hello Hello Hello Hello + +! Here's a list: +{ 2 4 6 8 } ! Goes on the stack as one item + +! Aqui está uma lista: +{ 2 4 6 8 } [ 1 + . ] each ! Exibe 3 5 7 9 +{ 2 4 6 8 } [ 1 + ] map ! Sai { 3 5 7 9 } na pilha + +! Reduzir laços ou criar listas: +{ 1 2 3 4 5 } [ 2 mod 0 = ] filter ! Mantém apenas membros da lista para os quais a citação é verdadeira: { 2 4 } +{ 2 4 6 8 } 0 [ + ] reduce . ! Como "fold" em linguagens funcionais: exibe 20 (0+2+4+6+8) +{ 2 4 6 8 } 0 [ + ] accumulate . . ! Como reduzir, mas mantém os valores intermediários em uma lista: exibe { 0 2 6 12 } então 20 +1 5 [ 2 * dup ] replicate . ! Repete a citação 5 vezes e coleta os resultados em uma lista: { 2 4 8 16 32 } +1 [ dup 100 < ] [ 2 * dup ] produce ! Repete a segunda citação até que a primeira retorne como falsa e colete os resultados: { 2 4 8 16 32 64 128 } + +! Se tudo mais falhar, uma finalidade geral, enquanto repete: +1 [ dup 10 < ] [ "Hello" . 1 + ] while ! Exibe "Hello" 10 vezes + ! Sim, é difícil de ler + ! Isso é o que todos esses loops variantes são para + +! Variáveis +! Normalmente, espera-se que os programas Factor mantenham todos os dados na pilha. +! Usar variáveis nomeadas torna a refatoração mais difícil (e é chamada de Factor por um motivo) +! Variáveis globais, se você precisar: + +SYMBOL: name ! Cria o nome como uma palavra identificadora +"Bob" name set-global ! Sem saída +name get-global . ! "Bob" + +! Variáveis locais nomeadas são consideradas uma extensão, mas estão disponíveis +! Em uma citação .. +[| m n ! A citação captura os dois principais valores da pilha em m e n + | m n + ] ! Leia-os + +! Ou em uma palavra.. +:: lword ( -- ) ! Note os dois pontos duplos para invocar a extensão da variável lexica + 2 :> c ! Declara a variável imutável c para manter 2 + c . ; ! Imprima isso + +! Em uma palavra declarada dessa maneira, o lado de entrada da declaração de pilha +! torna-se significativo e fornece os valores das variáveis em que os valores da pilha são capturados +:: double ( a -- result ) a 2 * ; + +! Variáveis são declaradas mutáveis ao terminar seu nome com um ponto de exclamação +:: mword2 ( a! -- x y ) ! Capture o topo da pilha na variável mutável a + a ! Empurrar a + a 2 * a! ! Multiplique por 2 e armazene o resultado em a + a ; ! Empurre novo valor de a +5 mword2 ! Pilha: 5 10 + +! Listas e Sequências +! Vimos acima como empurrar uma lista para a pilha + +0 { 1 2 3 4 } nth ! Acessar um membro específico de uma lista: 1 +10 { 1 2 3 4 } nth ! Error: índice de sequência fora dos limites +1 { 1 2 3 4 } ?nth ! O mesmo que nth se o índice estiver dentro dos limites: 2 +10 { 1 2 3 4 } ?nth ! Nenhum erro se estiver fora dos limites: f + +{ "at" "the" "beginning" } "Append" prefix ! { "Append" "at" "the" "beginning" } +{ "Append" "at" "the" } "end" suffix ! { "Append" "at" "the" "end" } +"in" 1 { "Insert" "the" "middle" } insert-nth ! { "Insert" "in" "the" "middle" } +"Concat" "enate" append ! "Concatenate" - strings are sequences too +"Concatenate" "Reverse " prepend ! "Reverse Concatenate" +{ "Concatenate " "seq " "of " "seqs" } concat ! "Concatenate seq of seqs" +{ "Connect" "subseqs" "with" "separators" } " " join ! "Connect subseqs with separators" + +! E se você quiser obter meta, as citações são seqüências e podem ser desmontadas.. +0 [ 2 + ] nth ! 2 +1 [ 2 + ] nth ! + +[ 2 + ] \ - suffix ! Quotation [ 2 + - ] + + +``` + +##Pronto para mais? + +* [Documentação do Factor](http://docs.factorcode.org/content/article-help.home.html) diff --git a/pt-br/fsharp-pt.html.markdown b/pt-br/fsharp-pt.html.markdown new file mode 100644 index 00000000..55966cda --- /dev/null +++ b/pt-br/fsharp-pt.html.markdown @@ -0,0 +1,639 @@ +--- +language: F# +filename: learnfsharp-pt.fs +contributors: + - ["Scott Wlaschin", "http://fsharpforfunandprofit.com"] + - ["Adelar da Silva Queiróz", "https://adelarsq.github.io"] +lang: pt-br +--- + +F# é uma linguagem de propósito geral funcional e orientada a objetos. É livre, de código aberto e executa em Linux, Mac, Windows e outros. + +Possui um sistema de tipagem poderoso que evita muitos erros em tempo de compilação. Para isto utilizando inferência de tipos, o que a faz se comportar como uma linguagem dinâmica. + +A sintaxe é diferente das linguagens do estilo C (C, C#, Java, etc): + +* Chaves não são usadas para delimitar blocos de código. Ao invés disso é utilizada indentação (semelhante ao Python). +* Espaços em branco são usados para separar parâmetros, ao invés de vírgulas. + +Se você deseja executar o código abaixo, copie e cole em [https://try.fsharp.org](https://try.fsharp.org), que é um REPL online. + +```fsharp + +// comentários de linhas únicas usam barras duplas +(* comentários de linhas múltiplas usam o par (* . . . *) + +-fim do comentário de linhas múltiplas- *) + +// ================================================ +// Sintaxe básica +// ================================================ + +// ------ "Variáveis" (mas não exatamente) ------ +// A palavra reservada "let" define um valor imutável +let myInt = 5 +let myFloat = 3.14 +let myString = "hello" // note que nenhum tipo é necessário + +// ------ Listas ------ +let twoToFive = [2; 3; 4; 5] // Colchetes criam uma lista com + // ponto e vírgula como delimitadores +let oneToFive = 1 :: twoToFive // :: cria uma lista com um novo primeiro elemento +// O resultado é [1; 2; 3; 4; 5] +let zeroToFive = [0; 1] @ twoToFive // @ concatena duas listas + +// IMPORTANTE: vírgulas nunca são usadas como delimitadores, somente ponto e vírgula! + +// ------ Funções ------ +// A palavra chave "let" também define nomes para funções. +let square x = x * x // Note que não são usados parêntesis +square 3 // Agora executando a função. Também sem parêntesis + +let add x y = x + y // Não use add (x,y)! Isto significa algo + // completamente diferente. +add 2 3 // Agora execute a função. + +// para definir uma função de múltiplas linhas apenas use indentação. Nenhum ponto e vírgula é necessário +let evens list = + let isEven x = x % 2 = 0 // Define "isEven"como uma sub função. Note + // que o operador de igualdade é um simples "=". + List.filter isEven list // List.filter é uma função da biblioteca padrão + // com dois parâmetros: uma função que retorna boolean + // e uma lista para verificar + +evens oneToFive // Agora executando a função + +// Usando parênteses é possível deixar mais clara a precedência. Neste exemplo, +// "map" é usado primeiro, com dois argumentos, então executa "sum" no resultado. +// Sem os parênteses, "List.map" seria passado como uma argumento para List.sum +let sumOfSquaresTo100 = + List.sum ( List.map square [1..100] ) + +// É possível redirecionar a saída de uma operação para a próxima usando pipe ("|>") +// Redirecimento de dados é algo comum em F#, similar a pipes Unix. + +// Aqui é a mesma função sumOfSquares escrita com pipe +let sumOfSquaresTo100piped = + [1..100] |> List.map square |> List.sum // "square" foi definido anteriormente + +// você pode definir lambdas (funções anônimas) usando a palavra reservada "fun" +let sumOfSquaresTo100withFun = + [1..100] |> List.map (fun x -> x * x) |> List.sum + +// Em F# não há a palavra chave "return". Funções sempre +// retornam o valor da última expressão usada. + +// ------ Casamento de padrões (Pattern Matching) ------ +// Match..with.. é um poderoso case/switch. +let simplePatternMatch = + let x = "a" + match x with + | "a" -> printfn "x is a" + | "b" -> printfn "x is b" + | _ -> printfn "x is something else" // sublinhado combina com qualquer coisa + +// F# não permite null por padrão -- deve-se usar um Option +// e então efetuar um casamento de padrão. +// Some(..) e None são análogos a Nullable +let validValue = Some(99) +let invalidValue = None + +// Neste exemplo, match..with casa com "Some" e "None", +// e também desconstrói o valor em "Some" ao mesmo tempo. +let optionPatternMatch input = + match input with + | Some i -> printfn "input is an int=%d" i + | None -> printfn "input is missing" + +optionPatternMatch validValue +optionPatternMatch invalidValue + +// ------ Escrevando na tela ------ +// As funções printf/printfn são similares às +// Console.Write/WriteLine encontradas no C#. +printfn "Printing an int %i, a float %f, a bool %b" 1 2.0 true +printfn "A string %s, and something generic %A" "hello" [1; 2; 3; 4] + +// Exitem também as funções sprintf/sprintfn para formatação de dados +// em uma string, semelhante à String.Format do C#. + +// ================================================ +// Mais sobre funções +// ================================================ + +// F# é uma liguagem verdadeiramente funcional -- funções fazem +// parte das classes e podem ser combinadas facilmente para criar +// poderosos construtores + +// Módulos podem usar um grupo de funções +// É necessário usar indentação para defini-las. +module FunctionExamples = + + // define uma função de soma + let add x y = x + y + + // básico uso de uma função + let a = add 1 2 + printfn "1 + 2 = %i" a + + // aplicação parcial de parâmetros + let add42 = add 42 + let b = add42 1 + printfn "42 + 1 = %i" b + + // composição para combinar funções + let add1 = add 1 + let add2 = add 2 + let add3 = add1 >> add2 + let c = add3 7 + printfn "3 + 7 = %i" c + + // funções de alta ordem + [1..10] |> List.map add3 |> printfn "new list is %A" + + // listas de funções e mais + let add6 = [add1; add2; add3] |> List.reduce (>>) + let d = add6 7 + printfn "1 + 2 + 3 + 7 = %i" d + +// ================================================ +// Listas e coleções +// ================================================ + +// Existem três tipos de coleções ordenadas: +// * Listas são o tipo mais básico de coleção imutável; +// * Arrays são mutáveis e mais eficientes; +// * Sequences são lazy e infinitas (semelhante a enumerator). +// +// Outras coleções incluem maps e conjuntos imutáveis +// mais todas as coleções padrões do .NET + +module ListExamples = + + // listas usam colchetes + let list1 = ["a"; "b"] + let list2 = "c" :: list1 // :: é usado para adicionar um elemento no início da lista + let list3 = list1 @ list2 // @ é o operador de concatenação + + // list comprehensions (generators) + let squares = [for i in 1..10 do yield i * i] + + // Um gerador de números primos + // - este usa a notação custa para casamento de padrões + // - (p::xs) significa 'primeiro :: cauda' da lista, e pode ser escrito como p :: xs + // isto significa que casa 'p' (o primeiro item da lista), e xs recebe o resto da lista + // que é chamdo de 'cons pattern' + // - usa a palavra chave 'rec', que é necessária quando se usa recursão + let rec sieve = function + | (p::xs) -> p :: sieve [ for x in xs do if x % p > 0 then yield x ] + | [] -> [] + let primes = sieve [2..50] + printfn "%A" primes + + // casamento de padrões (pattern matching) com listas + let listMatcher aList = + match aList with + | [] -> printfn "the list is empty" + | [first] -> printfn "the list has one element %A " first + | [first; second] -> printfn "list is %A and %A" first second + | first :: _ -> printfn "the list has more than two elements, first element %A" first + + listMatcher [1; 2; 3; 4] + listMatcher [1; 2] + listMatcher [1] + listMatcher [] + + // recursão usando listas + let rec sum aList = + match aList with + | [] -> 0 + | x::xs -> x + sum xs + sum [1..10] + + // ----------------------------------------- + // Funções da biblioteca padrão + // ----------------------------------------- + + // mapas + let add3 x = x + 3 + [1..10] |> List.map add3 + + // filtros + let even x = x % 2 = 0 + [1..10] |> List.filter even + + // muito mais -- veja a documentação + +module ArrayExamples = + + // arrays usam colchetes com barra vertical + let array1 = [| "a"; "b" |] + let first = array1.[0] // acesso por índice usando ponto + + // casamento de padrões (pattern matching) para arrays é feito da mesma forma que de listas + let arrayMatcher aList = + match aList with + | [| |] -> printfn "the array is empty" + | [| first |] -> printfn "the array has one element %A " first + | [| first; second |] -> printfn "array is %A and %A" first second + | _ -> printfn "the array has more than two elements" + + arrayMatcher [| 1; 2; 3; 4 |] + + // As funções da biblioteca padrão são as mesmas que para List + + [| 1..10 |] + |> Array.map (fun i -> i + 3) + |> Array.filter (fun i -> i % 2 = 0) + |> Array.iter (printfn "value is %i. ") + + +module SequenceExamples = + + // sequências usam chaves + let seq1 = seq { yield "a"; yield "b" } + + // sequências podem usar yield e + // podem conter subsequencias + let strange = seq { + // "yield" adiciona um elemento + yield 1; yield 2; + + // "yield!" adiciona uma subsequencia + yield! [5..10] + yield! seq { + for i in 1..10 do + if i % 2 = 0 then yield i }} + // teste + strange |> Seq.toList + + // Sequências podem ser criadas usando "unfold" + // Este é um exemplo da série de Fibonacci + let fib = Seq.unfold (fun (fst,snd) -> + Some(fst + snd, (snd, fst + snd))) (0,1) + + // teste + let fib10 = fib |> Seq.take 10 |> Seq.toList + printf "first 10 fibs are %A" fib10 + + +// ================================================ +// Tipos de dados +// ================================================ + +module DataTypeExamples = + + // Todos os dados são imutáveis por padrão + + // Tuplas são uma forma rápida de reprentar n elementos de tipos anônimos + // -- Use a vírgula para criar uma tupla + let twoTuple = 1, 2 + let threeTuple = "a", 2, true + + // Casamento de padrões (pattern match) para desconstruir + let x, y = twoTuple // atribui x = 1, y = 2 + + // ------------------------------------ + // O tipo registro possui nomes nos campos + // ------------------------------------ + + // Use "type" com chaves para definir um registro + type Person = {First:string; Last:string} + + // Use "let" com chaves para criar um registro + let person1 = {First="John"; Last="Doe"} + + // Casamento de padrões para desconstruir + let {First = first} = person1 // atribui first="John" + + // ------------------------------------ + // Tipos union (variantes) possuem um conjunto de escolhas + // Somente um caso pode ser válido por vez. + // ------------------------------------ + + // Use "type" com barra/pipe para definir um union + type Temp = + | DegreesC of float + | DegreesF of float + + // Use qualquer dos tipos para criar um + let temp1 = DegreesF 98.6 + let temp2 = DegreesC 37.0 + + // Casamento de padrões deve cobrir todos os tipos de definidos para desconstruir + let printTemp = function + | DegreesC t -> printfn "%f degC" t + | DegreesF t -> printfn "%f degF" t + + printTemp temp1 + printTemp temp2 + + // ------------------------------------ + // Tipos recursivos + // ------------------------------------ + + // Tipos podem ser combinados recursivamente de formas complexas + // sem ter que criar subclasses + type Employee = + | Worker of Person + | Manager of Employee list + + let jdoe = {First="John"; Last="Doe"} + let worker = Worker jdoe + + // ------------------------------------ + // Modelando com tipos + // ------------------------------------ + + // Tipos union são muito bons para modelagem de estados sem usar flags + type EmailAddress = + | ValidEmailAddress of string + | InvalidEmailAddress of string + + let trySendEmail email = + match email with // casamento de padrões + | ValidEmailAddress address -> () // envia + | InvalidEmailAddress address -> () // não envia + + // A combinação de tipos union e registros juntos + // provê uma grande fundação para DDD (Domain Driven Design). + // Você pode criar centenas de pequenos tipos que refletem + // exatamente o seu domínio. + + type CartItem = { ProductCode: string; Qty: int } + type Payment = Payment of float + type ActiveCartData = { UnpaidItems: CartItem list } + type PaidCartData = { PaidItems: CartItem list; Payment: Payment} + + type ShoppingCart = + | EmptyCart // nenhum dado + | ActiveCart of ActiveCartData + | PaidCart of PaidCartData + + // ------------------------------------ + // Comportamento padrão para tipos + // ------------------------------------ + + // Tipos padrões possuem um padrão já definido, não precisando de codificação nenhuma. + // * Imutáveis + // * Impressão formatada para depuração + // * Igualdade e comparação + // * Serialização + + // Impressão formatada usando %A + printfn "twoTuple=%A,\nPerson=%A,\nTemp=%A,\nEmployee=%A" + twoTuple person1 temp1 worker + + // Igualdade e comparação padrão. + // Um exemplo com cartas: + type Suit = Club | Diamond | Spade | Heart + type Rank = Two | Three | Four | Five | Six | Seven | Eight + | Nine | Ten | Jack | Queen | King | Ace + + let hand = [ Club, Ace; Heart, Three; Heart, Ace; + Spade, Jack; Diamond, Two; Diamond, Ace ] + + // ordenando + List.sort hand |> printfn "sorted hand is (low to high) %A" + List.max hand |> printfn "high card is %A" + List.min hand |> printfn "low card is %A" + + +// ================================================ +// Padrões ativos (Active patterns) +// ================================================ + +module ActivePatternExamples = + + // F# possui um tipo especial de casamento de padrões chamado "padrões ativos" ("active patterns") + // onde o padrão pode ser interpretado ou detectado dinamicamente. + + // parêntesis e barra são a sintaxe para "padrões ativos" + + // Você pode usar "elif" ao invés de "else if" em expressões condicionais. + // Elas são equivalentes em F# + + // por exemplo, defina um "padrão ativo" para tratar tipos de caracteres... + let (|Digit|Letter|Whitespace|Other|) ch = + if System.Char.IsDigit(ch) then Digit + elif System.Char.IsLetter(ch) then Letter + elif System.Char.IsWhiteSpace(ch) then Whitespace + else Other + + // ... e então use ele para interpretar de forma bem mais simples + let printChar ch = + match ch with + | Digit -> printfn "%c is a Digit" ch + | Letter -> printfn "%c is a Letter" ch + | Whitespace -> printfn "%c is a Whitespace" ch + | _ -> printfn "%c is something else" ch + + // imprima a lista + ['a'; 'b'; '1'; ' '; '-'; 'c'] |> List.iter printChar + + // ------------------------------------------------ + // FizzBuzz usando padrões ativos (active patterns) + // ------------------------------------------------ + + // É possível criar casamento de padrões parcial também + // Apenas use sublinhado para a definição, e retorne Some se casado. + let (|MultOf3|_|) i = if i % 3 = 0 then Some MultOf3 else None + let (|MultOf5|_|) i = if i % 5 = 0 then Some MultOf5 else None + + // a função principal + let fizzBuzz i = + match i with + | MultOf3 & MultOf5 -> printf "FizzBuzz, " + | MultOf3 -> printf "Fizz, " + | MultOf5 -> printf "Buzz, " + | _ -> printf "%i, " i + + // teste + [1..20] |> List.iter fizzBuzz + +// ================================================ +// Expressividade +// ================================================ + +module AlgorithmExamples = + + // F# possui uma alta razão sinais/ruídos, assim o código + // é lido praticamento como se descreve o algoritmo + + // ------ Exemplo: defina uma função que faça soma dos quadrados ------ + let sumOfSquares n = + [1..n] // 1) pega todos os números de 1 a n + |> List.map square // 2) eleva ao quadrado cada um + |> List.sum // 3) soma os resultados + + // teste + sumOfSquares 100 |> printfn "Sum of squares = %A" + + // ------ Examplo: defina uma função de ordenação ------ + let rec sort list = + match list with + // Se a lista está vazia + | [] -> + [] // retorna a lista vazia + // Se a lista não está vazia + | firstElem::otherElements -> // pega o primeiro elemento + let smallerElements = // extrai os elementos menores + otherElements // dos restantes + |> List.filter (fun e -> e < firstElem) + |> sort // e ordena eles + let largerElements = // extrai os elementos maiores + otherElements // dos restantes + |> List.filter (fun e -> e >= firstElem) + |> sort // e ordena eles + // Combine as 3 partes em uma nova lista e retorne ela + List.concat [smallerElements; [firstElem]; largerElements] + + // teste + sort [1; 5; 23; 18; 9; 1; 3] |> printfn "Sorted = %A" + +// ================================================ +// Código assíncrono +// ================================================ + +module AsyncExample = + + // F# possui suporte a funcionalidades para ajudar a escrever código assíncrono + // sem tornar o código difícil de manter ("pyramid of doom") + // + // O seguinte exemplo efetua download de um conjunto de páginas em paralelo. + + open System.Net + open System + open System.IO + open Microsoft.FSharp.Control.CommonExtensions + + // Obtém o conteúdo de cara página de forma assíncrona + let fetchUrlAsync url = + async { // a palavra chave "async" e chaves + // criam um objeto assíncrono + let req = WebRequest.Create(Uri(url)) + use! resp = req.AsyncGetResponse() + // use! é uma atribuição assíncrona + use stream = resp.GetResponseStream() + // "use" dispara automaticamente close() + // no recurso no fim do escopo + use reader = new IO.StreamReader(stream) + let html = reader.ReadToEnd() + printfn "finished downloading %s" url + } + + // uma lista de sites para fazer download + let sites = ["http://www.bing.com"; + "http://www.google.com"; + "http://www.microsoft.com"; + "http://www.amazon.com"; + "http://www.yahoo.com"] + + // efetue + sites + |> List.map fetchUrlAsync // cria uma lista de tarefas assíncronas + |> Async.Parallel // coloca as tarefas para executarem em paralelo + |> Async.RunSynchronously // inicia cada uma + +// ================================================ +// Compatibilidade com .NET +// ================================================ + +module NetCompatibilityExamples = + + // F# pode pode fazer praticamente tudo que C# pode fazer, e integra + // de forma simples com bibliotecas .NET e Mono + + // ------- usando uma função de uma biblioteca existente ------- + + let (i1success, i1) = System.Int32.TryParse("123"); + if i1success then printfn "parsed as %i" i1 else printfn "parse failed" + + // ------- Implementando interfaces de forma simples! ------- + + // cria um novo objeto que implementa IDisposable + let makeResource name = + { new System.IDisposable + with member this.Dispose() = printfn "%s disposed" name } + + let useAndDisposeResources = + use r1 = makeResource "first resource" + printfn "using first resource" + for i in [1..3] do + let resourceName = sprintf "\tinner resource %d" i + use temp = makeResource resourceName + printfn "\tdo something with %s" resourceName + use r2 = makeResource "second resource" + printfn "using second resource" + printfn "done." + + // ------- Código orientado a objetos ------- + + // F# também possui suporte a orientação a objetos. + // Possui suporte a classes, herança, métodos virtuais, etc. + + // interface com tipo genérico + type IEnumerator<'a> = + abstract member Current : 'a + abstract MoveNext : unit -> bool + + // classe base abstrata com métodos virtuais + [<AbstractClass>] + type Shape() = + // propriedades somente leitura + abstract member Width : int with get + abstract member Height : int with get + // método não virtual + member this.BoundingArea = this.Height * this.Width + // método virtual com implementação base + abstract member Print : unit -> unit + default this.Print () = printfn "I'm a shape" + + // classe concreta que herda da classe base e sobrescreve + type Rectangle(x:int, y:int) = + inherit Shape() + override this.Width = x + override this.Height = y + override this.Print () = printfn "I'm a Rectangle" + + // testes + let r = Rectangle(2, 3) + printfn "The width is %i" r.Width + printfn "The area is %i" r.BoundingArea + r.Print() + + // ------- métodos de extensão ------- + + // Assim como em C#, F# pode extender classes já existentes com métodos de extensão. + type System.String with + member this.StartsWithA = this.StartsWith "A" + + // testes + let s = "Alice" + printfn "'%s' starts with an 'A' = %A" s s.StartsWithA + + // ------- eventos ------- + + type MyButton() = + let clickEvent = new Event<_>() + + [<CLIEvent>] + member this.OnClick = clickEvent.Publish + + member this.TestEvent(arg) = + clickEvent.Trigger(this, arg) + + // teste + let myButton = new MyButton() + myButton.OnClick.Add(fun (sender, arg) -> + printfn "Click event with arg=%O" arg) + + myButton.TestEvent("Hello World!") + +``` + +## Mais Informações + +Para mais demonstrações de F# acesse [why use F#](http://fsharpforfunandprofit.com/why-use-fsharp/). + +Leia mais sobre F# em [fsharp.org](http://fsharp.org/) e [dotnet's F# page](https://dotnet.microsoft.com/languages/fsharp). diff --git a/pt-br/go-pt.html.markdown b/pt-br/go-pt.html.markdown index c7339831..31473ee1 100644 --- a/pt-br/go-pt.html.markdown +++ b/pt-br/go-pt.html.markdown @@ -16,7 +16,7 @@ A linguagem Go foi criada a partir da necessidade de ver trabalho feito. Não forma de resolver os problemas do mundo real. Tem conceitos familiares de linguagens imperativas com tipagem estática. É -rápida a compilar e rápida a executar, acrescentando mecanismos de concorrência +rápida para compilar e rápida para executar, acrescentando mecanismos de concorrência fáceis de entender para tirar partido dos CPUs multi-core de hoje em dia, e tem recursos para ajudar com a programação em larga escala. @@ -39,10 +39,10 @@ import ( ) // Definição de uma função. Main é especial. É o ponto de entrada para o -// programa executável. Goste-se ou não, a linguagem Go usa chavetas. +// programa executável. Goste-se ou não, a linguagem Go usa chaves. func main() { // A função Println envia uma linha para stdout. - // É necessário qualifica-la com o nome do pacote, fmt. + // É necessário qualificá-la com o nome do pacote, fmt. fmt.Println("Olá Mundo!") // Chama outra função dentro deste pacote. diff --git a/pt-br/groovy-pt.html.markdown b/pt-br/groovy-pt.html.markdown index 2ec7d967..3acfce21 100644 --- a/pt-br/groovy-pt.html.markdown +++ b/pt-br/groovy-pt.html.markdown @@ -1,7 +1,7 @@ --- language: Groovy category: language -filename: learngroovy.groovy +filename: learngroovy-pt.groovy contributors: - ["Roberto Pérez Alcolea", "http://github.com/rpalcolea"] translators: @@ -14,10 +14,10 @@ Groovy - Uma linguagem dinâmica para a plataforma Java. [Leia mais aqui.](http: ```groovy /* - Prepara-se: + Prepare-se: 1) Instale a máquina virtual de Groovy - http://gvmtool.net/ - 2) Intalse o Groovy: gvm install groovy + 2) Instale o Groovy: gvm install groovy 3) Inicie o console groovy digitando: groovyConsole */ @@ -104,7 +104,7 @@ tecnologiasOrdenadas = tecnologias.sort( false ) /*** Manipulando listas ***/ -//Substitue todos os elementos da lista +//Substitui todos os elementos da lista Collections.replaceAll(tecnologias, 'Gradle', 'gradle') //Desorganiza a lista @@ -159,7 +159,7 @@ println devMap.values() usará este campo. * Se você quer uma propriedade private ou protected, você deve prover seus - próprios getters e setter, que devem ser declarados como private ou protected. + próprios getters e setters, que devem ser declarados como private ou protected. * Se você acessar uma propriedade dentro da classe e esta propriedade é definida em tempo de compilação com 'this', implícito ou explícito (por exemplo, @@ -226,15 +226,17 @@ for (i in array) { //Itera sobre um mapa def map = ['name':'Roberto', 'framework':'Grails', 'language':'Groovy'] -x = 0 +x = "" for ( e in map ) { x += e.value + x += " " } +assert x.equals("Roberto Grails Groovy ") /* Operadores - Sobrecarregamento de Operadores para uma lsita dos operadores comuns que + Sobrecarga de Operadores para uma lista dos operadores comuns que Grooby suporta: http://www.groovy-lang.org/operators.html#Operator-Overloading @@ -252,7 +254,7 @@ def nomeUsuario = usuario?.nomeUsuario /* Closures - Um closure, em Grooby, é como um "bloco de código" ou um ponteiro para método. + Um closure, em Groovy, é como um "bloco de código" ou um ponteiro para método. É um pedação de código que é definido e executado em um momento posterior. Mais informação em: http://www.groovy-lang.org/closures.html @@ -267,7 +269,7 @@ clos() def soma = { a, b -> println a+b } soma(2,4) -//Closdures por referir-se a variáveis que não estão listadas em sua +//Closures podem referir-se a variáveis que não estão listadas em sua //lista de parêmetros. def x = 5 def multiplicarPor = { num -> num * x } @@ -307,7 +309,7 @@ chamaClosure(3, 4) /* Expando - A classe Expando é um bean dinâmico que permite adicionar propriedade e + A classe Expando é um bean dinâmico que permite adicionar propriedades e closures como métodos a uma instância desta classe http://mrhaki.blogspot.mx/2009/10/groovy-goodness-expando-as-dynamic-bean.html diff --git a/pt-br/haskell-pt.html.markdown b/pt-br/haskell-pt.html.markdown index 788dc1d2..c55a4c03 100644 --- a/pt-br/haskell-pt.html.markdown +++ b/pt-br/haskell-pt.html.markdown @@ -41,7 +41,7 @@ o desenvolvimento deste paradigma de programação. 7 * 7 -- 7 vezes 7 7 / 7 -- 7 dividido por 7 --- Divisões não são inteiras, são fracionádas por padrão da linguagem +-- Divisões não são inteiras, são fracionadas por padrão da linguagem 28736 / 82374 -- 0.3488479374559934 @@ -67,7 +67,7 @@ not False -- Nega uma falácia 7 > 7 -- 7 é maior que 7 ? -{- Haskell é uma linguagem que tem uma sintáxe bastante familiar na +{- Haskell é uma linguagem que tem uma sintaxe bastante familiar na matemática, por exemplo em chamadas de funções você tem: NomeFunção ArgumentoA ArgumentoB ArgumentoC ... @@ -93,7 +93,7 @@ not False -- Nega uma falácia "AbBbbcAbbcbBbcbcb" !! 2 -- 'B' ---------------------------------------------------- --- Listas e Túplas +-- 2. Listas e Túplas ---------------------------------------------------- -- A construção de uma lista precisa ser de elementos homogêneos diff --git a/pt-br/haxe-pt.html.markdown b/pt-br/haxe-pt.html.markdown new file mode 100644 index 00000000..13264dec --- /dev/null +++ b/pt-br/haxe-pt.html.markdown @@ -0,0 +1,795 @@ +--- +language: haxe +filename: LearnHaxe3-br.hx +contributors: + - ["Justin Donaldson", "https://github.com/jdonaldson/"] + - ["Dan Korostelev", "https://github.com/nadako/"] +translators: + - ["David Lima", "https://github.com/davelima/"] +lang: pt-br +--- + +Haxe é uma linguagem baseada na web que provê suporte a C++, C#, SWF/ActionScript, +Java e Neko byte code (também desenvolvida pelo autor de Haxe). Observe que +este guia é para a versão 3 de Haxe. Alguns pontos do guia são aplicáveis +para versões anteriores, mas é recomendado que você busque outras referências +para essas versões. + + +```csharp +/* + Bem vindo ao Aprenda Haxe 3 em 15 minutos. http://www.haxe.org + Este é um tutorial executável. Você pode compilar e rodar este tutorial + usando o compilador haxe, estando no mesmo diretório de LearnHaxe.hx: + $> haxe -main LearnHaxe3 -x out + + Olhe para os sinais de /* e */ em volta desses parágrafos. Nós estamos + dentro de um "Comentário multilinha". Nós podemos colocar observações aqui + e elas serão ignoradas pelo compilador. + + Comentários multilinha também são utilizados para gerar documentação haxedoc, + seguindo o estilo javadoc. Eles serão usados pelo haxedoc se precerem imediatamente + uma classe, uma função de uma classe ou uma variável de uma classe. + + */ + +// Duas barras, como as dessa linha, farão um comentário de linha única. + + +/* + Este será o primeiro código haxe de verdade, e está declarando um pacote vazio. + Não é necessário usar um pacote, mas ele será útil se você quiser criar + um namespace para o seu código (exemplo: org.seuapp.SuaClasse). + + Omitir a declaração de pacote é a mesma coisa que declarar um pacote vazio. + */ +package; // pacote vazio, sem namespace. + +/* + Pacotes são diretórios que contém módulos. Cada módulo é um arquivo .hx que + contém tipos definidos em um pacote. Nomes de pacotes (ex. org.seuapp) + devem estar em letras minúsculas, enquanto nomes de módulos devem começar + com uma letra maiúscula. Um módulo contem um ou mais tipos, cujo os nomes + também devem começar com uma letra maiúscula. + + Exemplo: a classe "org.seuapp.Foo" deve ter a estrutura de diretório org/module/Foo.hx, + sendo acessível do diretório do compilador ou caminho da classe. + + Se você importar código de outros arquivos, isso deve ser declarado antes + do restante do código. Haxe disponibiliza várias classes padrões para você + começar: + */ +import haxe.ds.ArraySort; + +// você pode importar várias classes/módulos de uma vez usando "*" +import haxe.ds.*; + +// você pode importar campos estáticos +import Lambda.array; + +// você também pode usar "*" para importar todos os campos estáticos +import Math.*; + +/* + Você também pode importar classes de uma forma diferente, habilitando-as para + extender a funcionalidade de outras classes, como um "mixin". Falaremos sobre + "using" em breve. + */ +using StringTools; + +/* + Typedefs são como variáveis... para tipos. Eles devem ser declarados antes + de qualquer código. Veremos isso em breve. + */ +typedef FooString = String; + +// Typedefs também podem referenciar tipos "estruturais". Também veremos isso em breve. +typedef FooObject = { foo: String }; + +/* + Esta é a definição da classe. É a classe principal do arquivo, visto que + possui o mesmo nome (LearnHaxe3) + */ +class LearnHaxe3{ + /* + Se você quiser que um determinado código rode automaticamente, você + precisa colocá-lo em uma função estática "main", e especificar a classe + nos argumentos do compilador. + Nesse caso, nós especificamos a classe "LearnHaxe3" no nos argumentos + do compilador acima. + */ + static function main(){ + + /* + Trace é o método padrão para imprimir expressões haxe na tela. + Temos diferentes métodos para conseguir isso em diferentes destinos. + Por exemplo: Java, C++, C#, etc. irão imprimir para stdout. + Javascript irá imprimir no console.log, e Flash irá imprimir para um + TextField anexado. Todos os "traces" imprimem também uma linha em branco + por padrão. Por fim, é possível prevenir um trace de ser exibido usando + o argumento "--no-traces" no compilador. + */ + trace("Olá mundo, com trace()!"); + + /* + Trace pode tratar qualquer tipo de valor ou objeto. O método tentará + imprimir a representação de uma expressão da melhor forma. Você também + pode concatenar strings usando o operador "+": + */ + trace( " Integer: " + 10 + " Float: " + 3.14 + " Boolean: " + true); + + /* + Em Haxe, é obrigatório separar expressões no mesmo bloco com ';'. Mas + é possível colocar duas expressões na mesma linha, dessa forma: + */ + trace('duas expressões..'); trace('uma linha'); + + + ////////////////////////////////////////////////////////////////// + // Tipos & Variáveis + ////////////////////////////////////////////////////////////////// + trace("***Tipos & Variáveis***"); + + /* + Vcoê pode atrelar valores e referências à estruturas usando a + palavra-chave "var": + */ + var um_inteiro:Int = 1; + trace(um_inteiro + " é o valor de um_inteiro"); + + + /* + Haxe é tipada estaticamente, então "um_inteiro" temos que declarar + um valor do tipo "Int", e o restante da expressão atrela o valor "1" + a esta variável. Em muitos casos, não é necessário declarar o tipo. + Aqui, o compilador haxe assume que o tipo de "outro_inteiro" deve + ser "Int" + */ + var outro_inteiro = 2; + trace(outro_inteiro + " é o valor de outro_inteiro"); + + // O método $type() imprime o tipo que o compilador assume: + $type(outro_inteiro); + + // Você também pode representar inteiros em hexadecimal: + var hex_inteiro = 0xffffff; + + /* + Haxe usa precisão de pltaforma para os tamanhos de Int e Float. + Ele também usa o comportamento de plataforma para sobrecarga. + (É possível ter outros tipos numéricos e comportamentos usando + bibliotecas especiais) + */ + + /* + Em adição a valores simples como Integers, Floats e Booleans, + Haxe disponibiliza implementações padrões de bibliotecas para + dados comuns de estrutura como strings, arrays, lists e maps: + */ + + var uma_string = "alguma" + 'string'; // strings podem estar entre aspas simples ou duplas + trace(uma_string + " é o valor de uma_string"); + + /* + Strings podem ser "interpoladas" se inserirmos variáveis em + posições específicas. A string deve estar entre aspas simples, e as + variáveis devem ser precedidas por "$". Expressões podem estar entre + ${...}. + */ + var x = 1; + var uma_string_interpolada = 'o valor de x é $x'; + var outra_string_interpolada = 'o valor de x + 1 é ${x + 1}'; + + /* + Strings são imutáveis, métodos retornarão uma cópia de partes + ou de toda a string. (Veja também a classe StringBuf) + */ + var uma_sub_string = a_string.substr(0,4); + trace(uma_sub_string + " é o valor de a_sub_string"); + + /* + Regex também são suportadas, mas não temos espaço suficiente para + entrar em muitos detalhes. + */ + var re = ~/foobar/; + trace(re.match('foo') + " é o valor de (~/foobar/.match('foo')))"); + + /* + Arrays são indexadas a partir de zero, dinâmicas e mutáveis. Valores + faltando são definidos como null. + */ + var a = new Array<String>(); // um array que contém Strings + a[0] = 'foo'; + trace(a.length + " é o valor de a.length"); + a[9] = 'bar'; + trace(a.length + " é o valor de a.length (depois da modificação)"); + trace(a[3] + " é o valor de a[3]"); // null + + /* + Arrays são *genéricas*, então você pode indicar quais valores elas + contém usando um parâmetro de tipo: + */ + var a2 = new Array<Int>(); // um Array de Ints + var a3 = new Array<Array<String>>(); // um Array de Arrays (de Strings). + + /* + Mapas são estruturas simples de chave/valor. A chave e o valor podem + ser de qualquer tipo. + */ + var m = new Map<String, Int>(); // As chaves são strings, os valores são Ints. + m.set('foo', 4); + // Você também pode usar a notação de array; + m['bar'] = 5; + trace(m.exists('bar') + " é o valor de m.exists('bar')"); + trace(m.get('bar') + " é o valor de m.get('bar')"); + trace(m['bar'] + " é o valor de m['bar']"); + + var m2 = ['foo' => 4, 'baz' => 6]; // Syntaxe alternativa de map + trace(m2 + " é o valor de m2"); + + /* + Lembre-se, você pode usar descoberta de tipo. O compilador + Haxe irá decidir o tipo da variável assim que você passar um + argumento que define um parâmetro de tipo. + */ + var m3 = new Map(); + m3.set(6, 'baz'); // m3 agora é Map<Int,String> + trace(m3 + " é o valor de m3"); + + /* + Haxe possui mais algumas estruturas de dados padrões no módulo haxe.ds, + tais como List, Stack e BalancedTree + */ + + + ////////////////////////////////////////////////////////////////// + // Operadores + ////////////////////////////////////////////////////////////////// + trace("***OPERADORES***"); + + // aritmética básica + trace((4 + 3) + " é o valor de (4 + 3)"); + trace((5 - 1) + " é o valor de (5 - 1)"); + trace((2 * 4) + " é o valor de (2 * 4)"); + trace((8 / 3) + " é o valor de (8 / 3) (divisão sempre produz Floats)"); + trace((12 % 4) + " é o valor de (12 % 4)"); + + + // comparação básica + trace((3 == 2) + " é o valor de 3 == 2"); + trace((3 != 2) + " é o valor de 3 != 2"); + trace((3 > 2) + " é o valor de 3 > 2"); + trace((3 < 2) + " é o valor de 3 < 2"); + trace((3 >= 2) + " é o valor de 3 >= 2"); + trace((3 <= 2) + " é o valor de 3 <= 2"); + + // operadores bit-a-bit padrões + /* + ~ Complemento bit-a-bit unário + << Deslocamento a esquerda + >> Deslocamento a direita + >>> Deslocamento a direita com preenchimento de 0 + & Bit-a-bit AND + ^ Bit-a-bit OR exclusivo + | Bit-a-bit OR inclusivo + */ + + // incrementos + var i = 0; + trace("Incrementos e decrementos"); + trace(i++); //i = 1. Pós-incremento + trace(++i); //i = 2. Pré-incremento + trace(i--); //i = 1. Pós-decremento + trace(--i); //i = 0. Pré-decremento + + ////////////////////////////////////////////////////////////////// + // Estruturas de controle + ////////////////////////////////////////////////////////////////// + trace("***ESTRUTURAS DE CONTROLE***"); + + // operadores if + var j = 10; + if (j == 10){ + trace("isto é impresso"); + } else if (j > 10){ + trace("não é maior que 10, então não é impresso"); + } else { + trace("também não é impresso."); + } + + // temos também um if "ternário": + (j == 10) ? trace("igual a 10") : trace("diferente de 10"); + + /* + Por fim, temos uma outra forma de estrutura de controle que opera + e na hora da compilação: compilação condicional. + */ +#if neko + trace('olá de neko'); +#elseif js + trace('olá de js'); +#else + trace('olá de outra plataforma!'); +#end + /* + O código compilado irá mudar de acordo com o alvo de plataforma. + Se estivermos compilando para neko (-x ou -neko), só teremos a + saudação de neko. + */ + + + trace("Loops e Interações"); + + // loop while + var k = 0; + while(k < 100){ + // trace(counter); // irá iprimir números de 0 a 99 + k++; + } + + // loop do-while + var l = 0; + do{ + trace("do sempre rodará pelo menos uma vez"); + } while (l > 0); + + // loop for + /* + Não há loop for no estilo C para Haxe, pois é propenso + a erros e não é necessário. Ao invés disso, Haxe possui + uma versão muito mais simples e segura que usa Iterators + (veremos isso logo mais). + */ + var m = [1,2,3]; + for (val in m){ + trace(val + " é o valor de val no array m"); + } + + // Perceba que você pode iterar em um índice usando uma lista limitada + // (veremos isso em breve também) + var n = ['foo', 'bar', 'baz']; + for (val in 0...n.length){ + trace(val + " é o valor de val (um índice de n)"); + } + + + trace("Compreensões de array"); + + // Compreensões de array servem para que você posse iterar um array + // enquanto cria filtros e modificações + var n_filtrado = [for (val in n) if (val != "foo") val]; + trace(n_filtrado + " é o valor de n_filtrado"); + + var n_modificado = [for (val in n) val += '!']; + trace(n_modificado + " é o valor de n_modificado"); + + var n_filtrado_e_modificado = [for (val in n) if (val != "foo") val += "!"]; + trace(n_filtrado_e_modificado + " é o valor de n_filtrado_e_modificado"); + + ////////////////////////////////////////////////////////////////// + // Blocos Switch (Tipos de valor) + ////////////////////////////////////////////////////////////////// + trace("***BLOCOS SWITCH (Tipos de valor)***"); + + /* + Blocos Switch no Haxe são muito poderosos. Além de funcionar com + valores básicos como strings e ints, também funcionam com tipos + algébricos em enums (falaremos sobre enums depois). + Veja alguns exemplos de valor básico por enquanto: + */ + var meu_cachorro = "fido"; + var coisa_favorita = ""; + switch(meu_cachorro){ + case "fido" : favorite_thing = "osso"; + case "rex" : favorite_thing = "sapato"; + case "spot" : favorite_thing = "bola de tênis"; + default : favorite_thing = "algum brinquedo desconhecido"; + // case _ : favorite_thing = "algum brinquedo desconhecido"; // mesma coisa que default + } + // O case "_" acima é um valor "coringa" que + // que funcionará para qualquer coisa. + + trace("O nome do meu cachorro é " + meu_cachorro + + ", e sua coisa favorita é: " + + coisa_favorita); + + ////////////////////////////////////////////////////////////////// + // Declarações de expressão + ////////////////////////////////////////////////////////////////// + trace("***DECLARAÇÕES DE EXPRESSÃO***"); + + /* + As declarações de controle em Haxe são muito poderosas pois + toda declaração também é uma expressão, considere o seguinte: + */ + + // declarações if + var k = if (true) 10 else 20; + + trace("k igual a ", k); // retorna 10 + + var outra_coisa_favorita = switch(meu_cachorro) { + case "fido" : "ursinho"; + case "rex" : "graveto"; + case "spot" : "bola de futebol"; + default : "algum brinquedo desconhecido"; + } + + trace("O nome do meu cachorro é " + meu cachorro + + ", e sua outra coisa favorita é: " + + outra_coisa_favorita); + + ////////////////////////////////////////////////////////////////// + // Convertendo tipos de valores + ////////////////////////////////////////////////////////////////// + trace("***CONVERTENDO TIPOS DE VALORES***"); + + // Você pode converter strings em ints de forma bem fácil. + + // string para int + Std.parseInt("0"); // retorna 0 + Std.parseFloat("0.4"); // retorna 0.4; + + // int para string + Std.string(0); // retorna "0"; + // concatenar com strings irá converter automaticamente em string. + 0 + ""; // retorna "0"; + true + ""; // retorna "true"; + // Veja a documentação de parseamento em Std para mais detalhes. + + + ////////////////////////////////////////////////////////////////// + // Lidando com Tipos + ////////////////////////////////////////////////////////////////// + + /* + Como mencionamos anteriormente, Haxe é uma linguagem tipada + estaticamente. Tipagem estática é uma coisa maravilhosa. Isto + permite autocompletar mais preciso, e pode ser usado para checar + completamente o funcionamento de um programa. Além disso, o compilador + Haxe é super rápido. + + *ENTRETANTO*, há momentos em que você espera que o compilador apenas + deixe algo passar, e não lance um "type error" em um determinado caso. + + Para fazer isso, Haxe tem duas palavras-chave separadas. A primeira + é o tipo "Dynamic": + */ + var din: Dynamic = "qualquer tipo de variável, assim como essa string"; + + /* + Tudo o que você sabe sobre uma variável Dynamic é que o compilador + não irá mais se preocupar com o tipo dela. É como uma variável + "coringa": você pode usar isso ao invés de qualquer tipo de variável, + e você pode atrelar qualquer valor a essa variável. + + A outra (e mais extrema) opção é a palavra-chave "untyped": + */ + + untyped { + var x:Int = 'foo'; // não faz sentido! + var y:String = 4; // loucura! + } + + /* + A palavra-chave "untyped" opera em *blocos* inteiros de código, + ignorando qualquer verificação de tipo que seria obrigatória em + outros casos. Essa palavra-chave deve ser usada com muita cautela, + como em situações limitadas de compilação condicional onde a + verificação de tipo pode ser um obstáculo. + + No geral, ignorar verificações de tipo *não* é recomendado. Use + os modelos de enum, herança ou estrutural para garantir o correto + funcionamento do seu programa. Só quando você tiver certeza de que + nenhum desses modelos funcionam no seu caso, você deve usar "Dynamic" + ou "untyped". + */ + + ////////////////////////////////////////////////////////////////// + // Programação básica orientada a objetos + ////////////////////////////////////////////////////////////////// + trace("***PROGRAMAÇÃO BÁSICA ORIENTADA A OBJETOS***"); + + + /* + Cria uma instância da FooClass. As definicções dessas classes + estão no final do arquivo. + */ + var instancia_foo = new FooClass(3); + + // lê a variável pública normalmente + trace(instancia_foo.variavel_publica + " é o valor de instancia_foo.variavel_publica"); + + // nós podemos ler essa variável + trace(instancia_foo.publica_leitura + " é o valor de instancia_foo.publica_leitura"); + // mas não podemos escrever nela + // instancia_foo.publica_leitura = 4; // isso irá causar um erro se descomentado: + // trace(instancia_foo.public_escrita); // e isso também. + + // chama o método toString: + trace(instancia_foo + " é o valor de instancia_foo"); + // mesma coisa: + trace(instancia_foo.toString() + " é o valor de instancia_foo.toString()"); + + + /* + A instancia_foo é do tipo "FooClass", enquanto acceptBarInstance + é do tipo BarClass. Entretanto, como FooClass extende BarClass, + ela é aceita. + */ + BarClass.acceptBarInstance(instancia_foo); + + /* + As classes abaixo têm mais alguns exemplos avançados, o método + "example()" executará esses exemplos aqui: + */ + SimpleEnumTest.example(); + ComplexEnumTest.example(); + TypedefsAndStructuralTypes.example(); + UsingExample.example(); + + } + +} + +/* + Essa é a "classe filha" do classe principal LearnHaxe3 + */ +class FooClass extends BarClass implements BarInterface{ + public var variavel_publica:Int; // variáveis públicas são acessíveis de qualquer lugar + public var publica_leitura (default, null): Int; // somente leitura pública habilitada + public var publica_escrita (null, default): Int; // somente escrita pública habilitada + public var property (get, set): Int; // use este estilo para habilitar getters e setters + + // variáveis privadas não estão disponíveis fora da classe. + // veja @:allow para formas de fazer isso. + var _private:Int; // variáveis são privadas se não forem marcadas como públicas + + // um construtor público + public function new(arg:Int){ + // chama o construtor do objeto pai, já que nós extendemos a BarClass: + super(); + + this.variavel_publica = 0; + this._private = arg; + + } + + // getter para _private + function get_property() : Int { + return _private; + } + + // setter para _private + function set_property(val:Int) : Int { + _private = val; + return val; + } + + // função especial que é chamada sempre que uma instância é convertida em string. + public function toString(){ + return _private + " com o método toString()!"; + } + + // essa classe precisa ter essa função definida, pois ela implementa + // a interface BarInterface + public function baseFunction(x: Int) : String{ + // converte o int em string automaticamente + return x + " foi passado pela baseFunction!"; + } +} + +/* + Uma classe simples para extendermos +*/ +class BarClass { + var base_variable:Int; + public function new(){ + base_variable = 4; + } + public static function acceptBarInstance(b:BarClass){ + } +} + +/* + Uma interface simples para implementarmos +*/ +interface BarInterface{ + public function baseFunction(x:Int):String; +} + +////////////////////////////////////////////////////////////////// +// Declarações Enum e Switch +////////////////////////////////////////////////////////////////// + +/* + Enums no Haxe são muito poderosos. Resumidamente, enums são + um tipo com um número limitado de estados: + */ + +enum SimpleEnum { + Foo; + Bar; + Baz; +} + +// Uma classe que faz uso desse enum: + +class SimpleEnumTest{ + public static function example(){ + var e_explicit:SimpleEnum = SimpleEnum.Foo; // você pode especificar o nome "completo" + var e = Foo; // bas descoberta de tipo também funciona. + switch(e){ + case Foo: trace("e era Foo"); + case Bar: trace("e era Bar"); + case Baz: trace("e era Baz"); // comente esta linha e teremos um erro. + } + + /* + Isso não parece tão diferente de uma alteração simples de valor em strings. + Entretanto, se nós não incluirmos *todos* os estados, o compilador + reclamará. Você pode testar isso comentando a linha mencionada acima. + + Você também pode especificar um valor padrão (default) para enums: + */ + switch(e){ + case Foo: trace("e é Foo outra vez"); + default : trace("default funciona aqui também"); + } + } +} + +/* + Enums vão muito mais além que estados simples, nós também + podemos enumerar *construtores*, mas nós precisaremos de um + exemplo mais complexo de enum: + */ +enum ComplexEnum{ + IntEnum(i:Int); + MultiEnum(i:Int, j:String, k:Float); + SimpleEnumEnum(s:SimpleEnum); + ComplexEnumEnum(c:ComplexEnum); +} +// Observação: O enum acima pode incluir *outros* enums também, incluindo ele mesmo! +// Observação: Isto é o que chamamos de *Tipos de dado algébricos* em algumas outras linguagens. + +class ComplexEnumTest{ + public static function example(){ + var e1:ComplexEnum = IntEnum(4); // especificando o parâmetro enum + /* + Agora nós podemos usar switch no enum, assim como extrair qualquer + parâmetros que ele possa ter. + */ + switch(e1){ + case IntEnum(x) : trace('$x foi o parâmetro passado para e1'); + default: trace("Isso não deve ser impresso"); + } + + // outro parâmetro aqui que também é um enum... um enum enum? + var e2 = SimpleEnumEnum(Foo); + switch(e2){ + case SimpleEnumEnum(s): trace('$s foi o parâmetro passado para e2'); + default: trace("Isso não deve ser impresso"); + } + + // enum dentro de enum dentro de enum + var e3 = ComplexEnumEnum(ComplexEnumEnum(MultiEnum(4, 'hi', 4.3))); + switch(e3){ + // Você pode buscar por certos enums aninhados especificando-os + // explicitamente: + case ComplexEnumEnum(ComplexEnumEnum(MultiEnum(i,j,k))) : { + trace('$i, $j, e $k foram passados dentro desse monstro aninhado.'); + } + default: trace("Isso não deve ser impresso"); + } + /* + Veja outros "tipos de dado algébricos" (GADT, do inglês) para mais + detalhes sobre o porque eles são tão úteis. + */ + } +} + +class TypedefsAndStructuralTypes { + public static function example(){ + /* + Aqui nós usaremos tipos typedef, ao invés de tipos base. + Lá no começo, nós definimos que o tipo "FooString" é um tipo "String". + */ + var t1:FooString = "alguma string"; + + /* + Aqui nós usamos typedefs para "tipos estruturais" também. Esses tipos + são definidos pela sua estrutura de campos, não por herança de classe. + Aqui temos um objeto anônimo com um campo String chamado "foo": + */ + + var anon_obj = { foo: 'hi' }; + + /* + A variável anon_obj não tem um tipo declarado, e é um objeto anônimo + de acordo com o compilador. Entretanto, lembra que lá no início nós + declaramos a typedef FooObj? Visto que o anon_obj tem a mesma estrutura, + nós podemos usar ele em qualquer lugar que um "FooObject" é esperado. + */ + + var f = function(fo:FooObject){ + trace('$fo foi passado para esta função'); + } + f(anon_obj); // chama a assinatura de FooObject com anon_obj. + + /* + Note que typedefs podem ter campos opcionais também, marcados com "?" + + typedef OptionalFooObj = { + ?optionalString: String, + requiredInt: Int + } + */ + + /* + Typedefs também funcionam com compilação condicional. Por exemplo, + nós poderíamos ter incluído isso no topo deste arquivo: + +#if( js ) + typedef Surface = js.html.CanvasRenderingContext2D; +#elseif( nme ) + typedef Surface = nme.display.Graphics; +#elseif( !flash9 ) + typedef Surface = flash8.MovieClip; +#elseif( java ) + typedef Surface = java.awt.geom.GeneralPath; +#end + + E teríamos apenas um tipo "Surface" para funcionar em todas + essas plataformas. + */ + } +} + +class UsingExample { + public static function example() { + + /* + A palavra-chave "using" é um tipo especial de import de classe que + altera o comportamento de qualquer método estático na classe. + + Neste arquivo, nós aplicamos "using" em "StringTools", que contém + alguns métodos estáticos para tratar tipos String. + */ + trace(StringTools.endsWith("foobar", "bar") + " deve ser verdadeiro!"); + + /* + Com um import "using", o primeiro argumento é extendido com o método. + O que isso significa? Bem, como "endsWith" tem um primeiro argumento + de tipo "String", isso significa que todos os tipos "String" agora + possuem o método "endsWith": + */ + trace("foobar".endsWith("bar") + " deve ser verdadeiro!"); + + /* + Essa técnica habilita uma grande quantidade de expressões para certos + tipos, e limita o escopo de modificações para um único arquivo. + + Note que a instância String *não* é modificada em tempo de execução. + O novo método adicionado não é uma parte da instância anexada, e o + compilador ainda irá gerar o código equivalente ao método estático. + */ + } + +} + +``` +Isso foi apenas o começo do que Haxe pode fazer. Para uma documentação de todos +os recursos de Haxe, veja o [manual](https://haxe.org/manual) e a +[documentação de API](https://api.haxe.org/). Para um diretório de bibliotecas de terceiros +disponíveis, veja a [Haxelib](https://lib.haxe.org/) + +Para tópicos mais avançados, dê uma olhada em: + +* [Tipos abstratos](https://haxe.org/manual/types-abstract.html) +* [Macros](https://haxe.org/manual/macro.html) +* [Recursos do compilador](https://haxe.org/manual/cr-features.html) + +Por fim, participe do [forum Haxe](https://community.haxe.org/), +ou no IRC [#haxe onfreenode](http://webchat.freenode.net/), ou no +[Chat Gitter](https://gitter.im/HaxeFoundation/haxe). diff --git a/pt-br/html-pt.html.markdown b/pt-br/html-pt.html.markdown new file mode 100644 index 00000000..22b7836e --- /dev/null +++ b/pt-br/html-pt.html.markdown @@ -0,0 +1,125 @@ +--- +language: html +filename: learnhtml-br.txt +contributors: + - ["Christophe THOMAS", "https://github.com/WinChris"] +translators: + - ["Robert Steed", "https://github.com/robochat"] +lang: pt-br +--- + +HTML é um acrônimo de HyperText Markup Language(Linguagem de Marcação de HiperTexto). +É uma linguagem que nos permite escrever páginas para a "world wide web". +É uma linguagem de marcação, nos permite escrever páginas na web usando código +para indicar como o texto e os dados serão ser exibidos. +De fato, arquivos HTML são simples arquivos de texto. +O que seria marcação? É um método de organização dos dados da página envolvidos +por abertura e fechamento de tags. +Essa marcação serve para dar significado ao texto que envolve. +Assim como outras linguagens, o HTML tem diversas versões. Aqui falaremos sobre o HTML5. + +**NOTA :** Você pode testar diferentes tags e elementos conforme progride os +tutoriais em sites como [codepen](http://codepen.io/pen/) podendo ver seus efeitos, +entendendo como funcionam e se familiarizando com a linguagem. +Esse artigo tem seu foco principal na sintaxe do HTML e algumas dicas úteis. + + +```html +<!-- Comentários são envolvidos conforme essa linha! --> + +<!-- #################### As Tags #################### --> + +<!-- Aqui está um exemplo de arquivo HTML que iremos analisar. --> + +<!doctype html> + <html> + <head> + <title>Meu Site</title> + </head> + <body> + <h1>Olá, mundo!</h1> + <a href = "http://codepen.io/anon/pen/xwjLbZ">Venha ver como isso aparece</a> + <p>Esse é um parágrafo.</p> + <p>Esse é um outro parágrafo.</p> + <ul> + <li>Esse é um item de uma lista não enumerada (bullet list)</li> + <li>Esse é um outro item</li> + <li>E esse é o último item da lista</li> + </ul> + </body> + </html> + +<!-- Um arquivo HTML sempre inicia indicando ao navegador que é uma página HTML. --> +<!doctype html> + +<!-- Após isso, inicia abrindo a tag <html>. --> +<html> + +<!-- Essa tag deverá ser fechada ao final do arquivo com </html>. --> +</html> + +<!-- Não deverá haver nada após o fechamento desta tag. --> + +<!-- Entre a abertura e o fechamento das tags <html></html>, nós encontramos: --> + +<!-- Um cabeçalho definido por <head> (deverá ser fechado com </head>). --> +<!-- O cabeçalho contém uma descrição e algumas informações adicionais que não serão exibidas; chamam-se metadados. --> + +<head> + <title>Meu Site</title><!-- Essa tag <title> indica ao navegador o título a ser exibido na barra de títulos e no nome da aba. --> +</head> + +<!-- Após a seção <head>, nós encontramos a tag - <body> --> +<!-- Até esse ponto, nada descrito irá aparecer na janela do browser. --> +<!-- Nós deveremos preencher o body(corpo) com o conteúdo a ser exibido. --> + +<body> + <h1>Olá, mundo!</h1> <!-- A tag h1 cria um título. --> + <!-- Há também subtítulos do <h1>, o mais importante, aos mais precisos (h6). --> + <a href = "http://codepen.io/anon/pen/xwjLbZ">Venha ver o que isso exibe</a> <!-- Um hiperlink ao endereço preenchido no atributo href="" --> + <p>Esse é um parágrafo.</p> <!-- A tag <p> permite incluir um texto na página. --> + <p>Esse é um outro parágrafo.</p> + <ul> <!-- A tag <ul> cria uma lista de marcação. --> + <!-- Para criar uma lista ordenada, devemos usar <ol>, exibindo 1. para o primeiro elemento, 2. para o segundo, etc. --> + <li>Esse é um item de uma lista não-enumerada.</li> + <li>Esse é um outro item</li> + <li>E esse é o último item da lista</li> + </ul> +</body> + +<!-- E é isso, criar um arquivo HTML pode ser bem simples. --> + +<!-- Também é possível adicionar alguns outros tipos de tags HTML. --> + +<!-- Para inserir uma imagem. --> +<img src="http://i.imgur.com/XWG0O.gif"/> <!-- O caminho da imagem deve ser indicado usando o atributo src="" --> +<!-- O caminho da imagem pode ser uma URL ou até mesmo o caminho do arquivo no seu computador. --> + +<!-- Também é possível criar uma tabela. --> + +<table> <!-- Iniciamos a tabela com a tag <table>. --> + <tr> <!-- <tr> nos permite criar uma linha. --> + <th>Primeiro cabeçalho</th> <!-- <th> nos permite criar o título de uma coluna. --> + <th>Segundo cabeçalho</th> + </tr> + <tr> + <td>Primeira linha, primeira coluna</td> <!-- <td> nos permite criar uma célula da tabela. --> + <td>Primeira linha, segunda coluna</td> + </tr> + <tr> + <td>Segunda linha, primeira coluna</td> + <td>Segunda linha, segunda coluna</td> + </tr> +</table> + +``` + +## Uso + +HTML é escrito em arquivos com a extensão `.html` ou `.htm`. Seu mime type é `text/html`. + +## Para aprender mais + +* [wikipedia](https://en.wikipedia.org/wiki/HTML) +* [HTML tutorial](https://developer.mozilla.org/en-US/docs/Web/HTML) +* [W3School](http://www.w3schools.com/html/html_intro.asp) diff --git a/pt-br/hy-pt.html.markdown b/pt-br/hy-pt.html.markdown index 5fa4df75..c69ac859 100644 --- a/pt-br/hy-pt.html.markdown +++ b/pt-br/hy-pt.html.markdown @@ -1,6 +1,6 @@ --- language: hy -filename: learnhy.hy +filename: learnhy-pt.hy contributors: - ["Abhishek L", "http://twitter.com/abhishekl"] translators: diff --git a/pt-br/java-pt.html.markdown b/pt-br/java-pt.html.markdown index db087a5f..1b9d7fc6 100644 --- a/pt-br/java-pt.html.markdown +++ b/pt-br/java-pt.html.markdown @@ -42,7 +42,7 @@ public class LearnJava { " Double: " + 3.14 + " Boolean: " + true); - // Para imprimir sem inserir uma nova lina, use o System.out.print + // Para imprimir sem inserir uma nova linha, use o System.out.print System.out.print("Olá "); System.out.print("Mundo"); @@ -407,7 +407,7 @@ class Velocipede extends Bicicleta { // Interfaces // Sintaxe de declaração de Interface -// <nível de acesso> Interface <nome-da-interface> extends <super-interfaces> { +// <nível de acesso> interface <nome-da-interface> extends <super-interfaces> { // // Constantes // // Declarações de método //} @@ -415,11 +415,15 @@ class Velocipede extends Bicicleta { // Exemplo - Comida: public interface Comestivel { public void comer(); // Qualquer classe que implementa essa interface, deve - // Implementar este método. + // implementar este método. } public interface Digestivel { public void digerir(); + // Em Java 8, interfaces podem ter métodos default. + // public void digerir() { + // System.out.println("digerindo ..."); + // } } @@ -438,7 +442,7 @@ public class Fruta implements Comestivel, Digestivel { } // Em Java, você pode estender somente uma classe, mas você pode implementar muitas -// Interfaces. Por exemplo: +// interfaces. Por exemplo: public class ClasseExemplo extends ExemploClassePai implements InterfaceUm, InterfaceDois { @@ -461,8 +465,8 @@ public class ClasseExemplo extends ExemploClassePai implements InterfaceUm, //} // Marcar uma classe como abstrata significa que ela contém métodos abstratos que devem -// ser definido em uma classe filha. Semelhante às interfaces, classes abstratas não podem -// ser instanciadas, ao invés disso devem ser extendidas e os métodos abstratos +// ser definidos em uma classe filha. Semelhante às interfaces, classes abstratas não podem +// ser instanciadas, ao invés disso devem ser estendidas e os métodos abstratos // definidos. Diferente de interfaces, classes abstratas podem conter uma mistura de // métodos concretos e abstratos. Métodos em uma interface não podem ter um corpo, // a menos que o método seja estático, e as variáveis sejam finais, por padrão, ao contrário de um @@ -482,7 +486,7 @@ public abstract class Animal // Não há necessidade de inicializar, no entanto, em uma interface // a variável é implicitamente final e, portanto, tem - // de ser inicializado. + // de ser inicializada. protected int idade; public void mostrarIdade() @@ -501,7 +505,7 @@ class Cachorro extends Animal { // Nota: ainda precisamos substituir os métodos abstratos na - // classe abstrata + // classe abstrata. @Override public void fazerSom() { @@ -532,13 +536,13 @@ class Cachorro extends Animal //} // Classes finais são classes que não podem ser herdadas e são, portanto, um -// filha final. De certa forma, as classes finais são o oposto de classes abstratas -// Porque classes abstratas devem ser estendidas, mas as classes finais não pode ser +// filho final. De certa forma, as classes finais são o oposto de classes abstratas, +// porque classes abstratas devem ser estendidas, mas as classes finais não podem ser // estendidas. public final class TigreDenteDeSabre extends Animal { // Nota: Ainda precisamos substituir os métodos abstratos na - // classe abstrata. + // classe abstrata. @Override public void fazerSom(); { @@ -552,7 +556,7 @@ public abstract class Mamifero() // Sintaxe de Métodos Finais: // <modificador-de-acesso> final <tipo-de-retorno> <nome-do-método>(<argumentos>) - // Métodos finais, como, classes finais não podem ser substituídas por uma classe filha, + // Métodos finais, como classes finais, não podem ser substituídos por uma classe filha, // e são, portanto, a implementação final do método. public final boolean EImpulsivo() { diff --git a/pt-br/javascript-pt.html.markdown b/pt-br/javascript-pt.html.markdown index e337f4bc..e38804f3 100644 --- a/pt-br/javascript-pt.html.markdown +++ b/pt-br/javascript-pt.html.markdown @@ -1,7 +1,8 @@ --- language: javascript +filename: javascript-pt.js contributors: - - ["Adam Brenecki", "http://adam.brenecki.id.au"] + - ["Leigh Brenecki", "https://leigh.net.au"] - ["Ariel Krakowski", "http://www.learneroo.com"] translators: - ["Willian Justen", "http://willianjusten.com.br"] @@ -19,12 +20,12 @@ que é um projeto que fornece um interpretador baseado no motor V8 do Google Chrome e está se tornando cada vez mais famoso. Feedback são muito apreciados! Você me encontrar em -[@adambrenecki](https://twitter.com/adambrenecki), ou -[adam@brenecki.id.au](mailto:adam@brenecki.id.au). +[@ExcitedLeigh](https://twitter.com/ExcitedLeigh), ou +[l@leigh.net.au](mailto:l@leigh.net.au). ```js // Comentários são como em C. Comentários de uma linha começam com duas barras, -/* e comentários de múltplas linhas começam com barra-asterisco +/* e comentários de múltiplas linhas começam com barra-asterisco e fecham com asterisco-barra */ // comandos podem ser terminados com ; @@ -360,7 +361,7 @@ myObj.myFunc(); // = "Olá mundo!" var myFunc = myObj.myFunc; myFunc(); // = undefined -// Inversamente, uma função pode ser atribuída a um objeto e ganhar a acesso +// Inversamente, uma função pode ser atribuída à um objeto e ganhar a acesso // através do `this`, até mesmo se ela não for chamada quando foi definida. var myOtherFunc = function(){ return this.myString.toUpperCase(); @@ -415,7 +416,7 @@ myNewObj.myNumber; // = 5 // vai olhar imediatamente para o seu prototype. // Algumas implementações em JS deixam você acessar o objeto prototype com a -// propriedade mágica `__proto__`. Enquanto isso é util para explicar +// propriedade mágica `__proto__`. Enquanto isso é útil para explicar // prototypes, não é parte de um padrão; nós vamos falar de algumas formas de // usar prototypes depois. @@ -488,7 +489,7 @@ if (0){ } // Entretanto, esses objetos encapsulados e as funções originais compartilham -// um mesmo prototype, portanto você pode adicionar funcionalidades a uma string, +// um mesmo prototype, portanto você pode adicionar funcionalidades à uma string, // por exemplo. String.prototype.firstCharacter = function(){ return this.charAt(0); diff --git a/pt-br/json-pt.html.markdown b/pt-br/json-pt.html.markdown index fd822c03..62d9ccad 100644 --- a/pt-br/json-pt.html.markdown +++ b/pt-br/json-pt.html.markdown @@ -16,7 +16,7 @@ Como JSON é um formato de intercâmbio de dados, este será, muito provavelment JSON na sua forma mais pura não tem comentários, mas a maioria dos analisadores aceitarão comentários no estilo C (//, /\* \*/). No entanto estes devem ser evitados para otimizar a compatibilidade. -Um valor JSON pode ser um numero, uma string, um array, um objeto, um booleano (true, false) ou null. +Um valor JSON pode ser um número, uma string, um array, um objeto, um booleano (true, false) ou null. Os browsers suportados são: Firefox 3.5+, Internet Explorer 8.0+, Chrome 1.0+, Opera 10.0+, e Safari 4.0+. diff --git a/pt-br/julia-pt.html.markdown b/pt-br/julia-pt.html.markdown index 48d97e58..52675bf5 100644 --- a/pt-br/julia-pt.html.markdown +++ b/pt-br/julia-pt.html.markdown @@ -8,7 +8,7 @@ translators: lang: pt-br --- -Julia é uma linguagem homoiconic funcional focada na computação tecnica. Ao mesmo tempo que ela tem todo o poder dos homoiconic macros, funções de primeira classe, e controle de baixo nivel, Julia é tão facil para aprender e usar quanto Python. +Julia é uma linguagem homoicônica funcional focada na computação técnica. Ao mesmo tempo que ela tem todo o poder dos macros homoicônicos, funções de primeira classe, e controle de baixo nível, Julia é tão fácil para aprender e usar quanto Python. Este tutorial é baseado no Julia 0.3. @@ -104,7 +104,7 @@ println("Eu sou Julia. Prazer em conhece-lo!") ## 2. Variáveis e coleções #################################################### -#Você não declara variáveis antes de atribui-lás. +#Você não declara variáveis antes de atribui-las. some_var = 5 # => 5 some_var # => 5 diff --git a/pt-br/kotlin-pt.html.markdown b/pt-br/kotlin-pt.html.markdown new file mode 100644 index 00000000..bbe8c0d1 --- /dev/null +++ b/pt-br/kotlin-pt.html.markdown @@ -0,0 +1,384 @@ +--- +language: kotlin +filename: LearnKotlin-pt.kt +contributors: + - ["S Webber", "https://github.com/s-webber"] +translators: + - ["Márcio Torres", "https://github.com/marciojrtorres"] +lang: pt-br +--- + +Kotlin é uma linguagem de programação estaticamente tipada para a JVM, Android e navegadores web. Ela é 100% interoperável com Java. +[Leia mais aqui.](https://kotlinlang.org/) + +```kotlin +// Comentários de uma linha iniciam com // +/* +Comentários multilinha se parecem com este. +*/ + +// A palavra-chave "package" funciona do mesmo modo que no Java. +package com.learnxinyminutes.kotlin + +/* +O ponto de entrada para um programa em Kotlin é uma função chamada "main" +Esta função recebe um vetor contendo quaisquer argumentos da linha de comando +*/ +fun main(args: Array<String>) { + /* + A declaração de valores pode ser feita tanto com "var" como "val" + Declarações com "val" não podem ser reatribuídas, enquanto com "var" podem. + */ + val umVal = 10 // não se poderá reatribuir qualquer coisa a umVal + var umVar = 10 + umVar = 20 // umVar pode ser reatribuída, mas respeitando o tipo + + /* + Na maioria dos casos Kotlin pode inferir o tipo, então não é preciso sempre + especificar o tipo explicitamente, mas quando o fazemos é assim: + */ + val umInteiro: Int = 7 + + /* + Strings podem ser representadas de forma semelhante a Java. + A contrabarra realiza o "escape", da mesma forma. + */ + val umaString = "Minha String está aqui!" + val outraString = "Imprimir na outra linha?\nSem problema!" + val maisString = "Você quer adicionar um tab?\tSem problema!" + println(umaString) + println(outraString) + println(maisString) + + /* + Uma string bruta é delimitada com três aspas ("""). + Strings brutas podem conter novas linhas e outros caracteres. + */ + val umaStringBruta = """ +fun olaMundo(val nome : String) { + println("Olá, mundo!") +} +""" + println(umaStringBruta) + + /* + As strings podem conter expressões modelo (template). + Uma expressão modelo começa com um cifrão ($). + É semelhante à interpolação de Strings em Ruby. + */ + val umaStringModelo = "$umaString tem ${umaString.length} caracteres" + println(umaStringModelo) + + /* + Para uma variável receber null deve-se explicitamente declará-la + como anulável. + A declaração de anulável é realizada incluindo uma "?" ao fim do tipo. + Pode-se acessar uma variável anulável usando o operador "?." + Usa-se o operador "?:" (também conhecido como operador Elvis) para + atribuir um valor alternativo para quando uma variável é nula. + */ + var umaVariavelAnulavel: String? = "abc" + println(umaVariavelAnulavel?.length) // => 3 + println(umaVariavelAnulavel?.length ?: -1) // => 3 + umaVariavelAnulavel = null + println(umaVariavelAnulavel?.length) // => null + println(umaVariavelAnulavel?.length ?: -1) // => -1 + + /* + Funções podem ser declaradas usando a palavra-chave "fun" + Os parâmetros da função são declarados entre parênteses logo + após o nome da função. + Os parâmetros da função podem ter opcionalmente um valor padrão. + O tipo de retorno da função, se necessário, é especificado após os argumentos. + */ + fun ola(nome: String = "mundo"): String { + return "Olá, $nome!" + } + println(ola("você")) // => Olá, você! + println(ola(nome = "tu")) // => Olá, tu! + println(ola()) // => Olá, mundo! + + /* + Um parâmetro pode ser declarado com a palavra-chave "vararg" para + permitir que seja passado um número variável de argumentos. + */ + fun exemploVarArg(vararg numeros: Int) { + println("Foram recebidos ${numeros.size} argumentos") + } + exemploVarArg() // => Passando nenhum argumento (0 argumentos) + exemploVarArg(1) // => Passando 1 argumento + exemploVarArg(1, 2, 3) // => Passando 3 argumentos + + /* + Quando uma função consiste numa única expressão as chaves + podem ser omitidas e o corpo declarado após o símbolo de "=" + */ + fun impar(x: Int): Boolean = x % 2 == 1 + println(impar(6)) // => false + println(impar(7)) // => true + + // O tipo de retorno não precisa ser declarado se pode ser inferido. + fun impar(x: Int) = x % 2 == 0 + println(impar(6)) // => true + println(impar(7)) // => false + + // Funções podem receber e retornar outras funções + fun nao(f: (Int) -> Boolean): (Int) -> Boolean { + return {n -> !f.invoke(n)} + } + // Funções nomeadas podem ser passadas como argumento usando o operador "::" + val naoImpar = nao(::impar) + val naoPar = nao(::par) + // Expressões Lambda podem ser usadas como argumentos + val naoZero = nao {n -> n == 0} + /* + Se uma lambda têm apenas um parâmetro sua declaração pode ser omitida, + incluindo o símbolo "->". + Neste caso o nome do único parâmetro deve ser "it". + */ + val naoPositivo = nao {it > 0} + for (i in 0..4) { + println("${naoImpar(i)} ${naoPar(i)} ${naoZero(i)} ${naoPositivo(i)}") + } + + // A palavra-chave "class" é usada para declarar classes + class ClasseExemplo(val x: Int) { + fun funcaoMembro(y: Int): Int { // ou "método" + return x + y + } + + infix fun funcaoMembroInfixa(y: Int): Int { + return x * y + } + } + /* + Para criar uma nova instância chama-se o construtor. + Note que Kotlin não tem a palavra-chave "new". + */ + val umaInstanciaDaClasseExemplo = ClasseExemplo(7) + // Funções membro (métodos) podem ser chamados usando a notação ponto "." + println(umaInstanciaDaClasseExemplo.funcaoMembro(4)) // => 11 + /* + Se uma função foi declarada com a palavra-chave "infix" então + ela pode ser invocada com a notação infixa. + */ + println(umaInstanciaDaClasseExemplo funcaoMembroInfixa 4) // => 28 + + /* + Classes de dados são um modo sucinto de criar classes que servem apenas + para guardar informações. + Os métodos "hashCode", "equals" e "toString" são gerados automaticamente. + */ + data class ExemploClasseDados (val x: Int, val y: Int, val z: Int) + val objetoDados = ExemploClasseDados(1, 2, 4) + println(objetoDados) // => ExemploClasseDados(x=1, y=2, z=4) + + // Classes de dados têm uma função "copy" + val dadosCopia = objetoDados.copy(y = 100) + println(dadosCopia) // => ExemploClasseDados(x=1, y=100, z=4) + + // Objetos podem ser desestruturados em múltiplas variáveis. + val (a, b, c) = dadosCopia + println("$a $b $c") // => 1 100 4 + + // desestruturando em um laço "for" + for ((a, b, c) in listOf(objetoDados)) { + println("$a $b $c") // => 1 100 4 + } + + val mapaDados = mapOf("a" to 1, "b" to 2) + // Map.Entry também é desestruturável + for ((chave, valor) in mapaDados) { + println("$chave -> $valor") + } + + // A função "with" é semelhante à declaração "with" do JavaScript + data class ExemploClasseDadosMutaveis (var x: Int, var y: Int, var z: Int) + val objDadosMutaveis = ExemploClasseDadosMutaveis(7, 4, 9) + with (objDadosMutaveis) { + x -= 2 + y += 2 + z-- + } + println(objDadosMutaveis) // => ExemploClasseDadosMutaveis(x=5, y=6, z=8) + + /* + Pode-se criar uma lista usando a função "listOf". + A lista é imutável, isto é, elementos não podem ser adicionados ou removidos. + */ + val umaLista = listOf("a", "b", "c") + println(umaLista.size) // => 3 + println(umaLista.first()) // => a + println(umaLista.last()) // => c + // Elementos de uma lista podem ser acessados pelo índice + println(umaLista[1]) // => b + + // Uma lista mutável pode ser criada com a função "mutableListOf". + val umaListaMutavel = mutableListOf("a", "b", "c") + umaListaMutavel.add("d") + println(umaListaMutavel.last()) // => d + println(umaListaMutavel.size) // => 4 + + // Similarmente, pode-se criar um conjunto com a função "setOf". + val umConjunto = setOf("a", "b", "c") + println(umConjunto.contains("a")) // => true + println(umConjunto.contains("z")) // => false + + // Da mesma forma que um mapa com a função "mapOf". + val umMapa = mapOf("a" to 8, "b" to 7, "c" to 9) + // Os valores contidos no mapa podem ser acessados pela sua chave. + println(umMapa["a"]) // => 8 + + /* + Sequências representam coleções avaliadas "preguiçosamente" (sob demanda). + Pode-se criar uma sequência usando a função "generateSequence". + */ + val umaSequencia = generateSequence(1, { it + 1 }) + val x = umaSequencia.take(10).toList() + println(x) // => [1, 2, 3, 4, 5, 6, 7, 8, 9, 10] + + // Um exemplo de uma sequência usada para gerar Números de Fibonacci: + fun sequenciaFibonacci(): Sequence<Long> { + var a = 0L + var b = 1L + + fun proximo(): Long { + val resultado = a + b + a = b + b = resultado + return a + } + + return generateSequence(::proximo) + } + val y = sequenciaFibonacci().take(10).toList() + println(y) // => [1, 1, 2, 3, 5, 8, 13, 21, 34, 55] + + // Kotlin oferece funções de alta-ordem para trabalhar com coleções. + val z = (1..9).map {it * 3} + .filter {it < 20} + .groupBy {it % 2 == 0} + .mapKeys {if (it.key) "par" else "impar"} + println(z) // => {impar=[3, 9, 15], par=[6, 12, 18]} + + // Um "for" pode ser usado com qualquer coisa que ofereça um "iterator" + for (c in "salve") { + println(c) + } + + // O "while" funciona da mesma forma que em outras linguagens. + var contador = 0 + while (contador < 5) { + println(contador) + contador++ + } + do { + println(contador) + contador++ + } while (contador < 10) + + /* + "if" pode ser usado como uma expressão que retorna um valor. + Por este motivo o operador ternário "? :" não é necessário em Kotlin. + */ + val numero = 5 + val mensagem = if (numero % 2 == 0) "par" else "impar" + println("$numero é $mensagem") // => 5 é impar + + // "when" pode ser usado como alternativa às correntes de "if-else if". + val i = 10 + when { + i < 7 -> println("primeiro block") + umaString.startsWith("oi") -> println("segundo block") + else -> println("bloco else") + } + + // "when" pode ser usado com um argumento. + when (i) { + 0, 21 -> println("0 ou 21") + in 1..20 -> println("entre 1 e 20") + else -> println("nenhum dos anteriores") + } + + // "when" pode ser usada como uma função que retorna um valor. + var resultado = when (i) { + 0, 21 -> "0 ou 21" + in 1..20 -> "entre 1 e 20" + else -> "nenhum dos anteriores" + } + println(resultado) + + /* + Pode-se verificar se um objeto é de um certo tipo usando o operador "is". + Se o objeto passar pela verificação então ele pode ser usado como + este tipo, sem a necessidade de uma coerção (cast) explícita (SmartCast). + */ + fun exemploSmartCast(x: Any) : Boolean { + if (x is Boolean) { + // x é automaticamente coagido para Boolean + return x + } else if (x is Int) { + // x é automaticamente coagido para Int + return x > 0 + } else if (x is String) { + // x é automaticamente coagido para String + return x.isNotEmpty() + } else { + return false + } + } + println(exemploSmartCast("Olá, mundo!")) // => true + println(exemploSmartCast("")) // => false + println(exemploSmartCast(5)) // => true + println(exemploSmartCast(0)) // => false + println(exemploSmartCast(true)) // => true + + // O Smartcast também funciona com blocos "when" + fun exemploSmartCastComWhen(x: Any) = when (x) { + is Boolean -> x + is Int -> x > 0 + is String -> x.isNotEmpty() + else -> false + } + + /* + As extensões são uma maneira nova de adicionar funcionalidades a classes. + Elas são similares aos "extension methods" da linguagem C#. + */ + fun String.remove(c: Char): String { + return this.filter {it != c} + } + println("olá, mundo!".remove('o')) // => lá, mund! + + println(ExemploEnum.A) // => A + println(ExemploObjeto.ola()) // => olá +} + +// Classes Enum são similares aos "enum types" do Java. +enum class ExemploEnum { + A, B, C +} + +/* +A palavra-chave "object" pode ser usar para criar Singletons. +Eles não são instanciados, mas podem referenciar sua instância única pelo nome. +É semelhante aos "singleton objects" da linguagem Scala. +*/ +object ExemploObjeto { + fun ola(): String { + return "olá" + } +} + +fun usaObjeto() { + ExemploObjeto.ola() + val algumaReferencia: Any = ExemploObjeto // usa-se o nome diretamente +} + +``` + +### Leitura Adicional + +* [Tutoriais de Kotlin](https://kotlinlang.org/docs/tutorials/)(EN) +* [Experimente Kotlin no seu navegador](http://try.kotlinlang.org/)(EN) +* [Uma lista de material sobre Kotlin](http://kotlin.link/)(EN) diff --git a/pt-br/latex-pt.html.markdown b/pt-br/latex-pt.html.markdown new file mode 100644 index 00000000..58586522 --- /dev/null +++ b/pt-br/latex-pt.html.markdown @@ -0,0 +1,291 @@ +--- +language: latex +contributors: + - ["Chaitanya Krishna Ande", "http://icymist.github.io"] + - ["Colton Kohnke", "http://github.com/voltnor"] + - ["Sricharan Chiruvolu", "http://sricharan.xyz"] + - ["Ramanan Balakrishnan", "https://github.com/ramananbalakrishnan"] + - ["Svetlana Golubeva", "https://attillax.github.io/"] +translators: + - ["Paulo Henrique Rodrigues Pinheiro", "https://github.com/paulohrpinheiro"] +lang: pt-br +filename: learn-latex-pt.tex +--- + +```tex +% Todas as linhas de comentários começam com % +% Não existem comentários multilinhas + +$ LaTeX não é um programa processador de textos "Visual" como +% MS Word ou OpenOffice Writer + +$ Todo comando LaTeX começa com uma barra invertida (\) + +% Documentos LaTeX começam com a definição do tipo que será % compilado +% Os tipos de documento podem ser livro, relatório, apresentação, etc. +% As opções para um documento aparecem entre [] chaves. Nesse caso +% está especificado que queremos o tamanho da fonte em 12pt. +\documentclass[12pt]{article} + +% Em seguida definimos os pacotes que o documento usa. +% Se você quiser incluir gráficos, texto colorido, ou código fonte de outra +% linguagem em outro arquivo em seu documento, você precisa ampliar as +% capacidades do LaTeX. Isso é feito adicionando-se pacotes. +% Serão incluídos os pacotes float e caption para imagens e hyperref +% para links. +\usepackage{caption} +\usepackage{float} +\usepackage{hyperref} + +% Para poder usar caracteres acentuados, use o seguinte pacote: +\usepackage[utf8]{inputenc} + +% Podemos definir algumas outras propriedades do documento também! +\author{Chaitanya Krishna Ande, Colton Kohnke, Sricharan Chiruvolu \& \\ +Svetlana Golubeva} +\date{\today} +\title{Aprenda \LaTeX \hspace{1pt} em Y Minutos!} + +% Agora estamos prontos para começar o documento +% Tudo antes dessa linha é chamado "preâmbulo". +\begin{document} +% Se informarmos os campos author (autores), date (data), "title" (título), +% LaTeX poderá cria uma página inicial para nós. +\maketitle +% Se tivermos seções, poderemos criar uma tabela de conteúdo. Para isso, +% o documento deve ser compilado duas vezes, para que tudo apareça na ordem +% correta. +% É uma boa prática separar a tabela de conteúdo do corpo do documento. Para +% isso usa-se o comando \newpage +\newpage +\tableofcontents + +\newpage + +% Muitos artigos de pesquisa possuem um resumo, e pode-se usar comandos +% predefinidos para isso. +% Isso deve aparecer em sua ordem lógica, portanto, após o topo, +% mas antes das seções principais do corpo. +% Esse comando está disponível para os documentos do tipo artigo (article) +% e relatório (report). +\begin{abstract} + Documentação do \LaTeX \hspace{1pt} escrita em \LaTeX! Nada original! +\end{abstract} + +% Comandos para seções são intuitivos. +% Todos os títulos de seção são adicionados automaticamente à tabela de conteúdo. +\section{Introdução} +Olá, meu nome é Colton e juntos estamos explorando o mundo do \LaTeX! + +\section{Outra seção} +Esse é o texto para outra seção. Penso que precisamos de uma subseção. + +\subsection{Isso é uma subseção} % Subseções também são intuitivas. +Penso que precisamos de mais uma + +\subsubsection{Pythagoras} +Muito melhor agora. +\label{subsec:pythagoras} + +% Ao usar o asterisco nós impedimos a numeração automática. +% Isso funciona para outros comandos \LaTeX também. +\section*{Essa é uma seção não numerada} +Afinal nem todas as seções precisam ser numeradas! + +\section{Algumas notas sobre texto} +%\section{Espaçamento % É necessário mais informação sobre intervalos de espaço. +\LaTeX \hspace{1pt} geralmente é muito bom sobre colocar texto onde ele deve +ser posto. Se +uma linha \\ deve \\ ser \\ quebrada \\ adicione \textbackslash\textbackslash +\hspace{1pt} ao código de seu documento. \\ + +\section{Listas} +Listas são uma das coisas mais fáceis de criar no \LaTeX! Preciso fazer compras +amanhã, então façamos uma lista de compras. +\begin{enumerate} % Isso cria o bloco "enumerate". + % \item faz com que o enumerate incremente + \item Salada. + \item 27 melancias. + \item Uma lebre. + % pode-se também sobrescrever o número do item usando [] + \item[quantas?] Pistolas de água médias. + + Não é um item da lista, mas faz parte do bloco enumerate. + + \end{enumerate} % Todos os blocos devem ter um final (end{}). + +\section{Matemática} + +Um dos usos iniciais para \LaTeX \hspace{1pt} foi a produção de artigos +acadêmicos e técnicos. Usualmente nos campos da matemática e ciência. Assim, é +necessários que consigamos incluir alguns símbolos especiais em nosso texto! \\ + +A matemática tem muitos símbolos, além dos quais se pode encontrar no teclado; +símbolos para relações e conjuntos, setas, operadores, e letras gregas, apenas +para mencionar alguns.\\ + +Conjuntos e relações são essenciais em muitos textos de pesquisa em matemática. +Aqui está como você pode indicar como todo x que pertence +a X, $\forall$ x $\in$ X. \\ +% Perceba que é necessário adicionar os sinais $ antes e depois dos símbolos. +% Isso é porque quando escrevendo, estamos em modo texto. +% Mas os símbolos de matemática só existem no modo matemática. +% Podemos entrar no modo matemática a partir do modo texto com os símbolos $. +% O oposto também pode ocorrer. Variáveis podem ser renderizadas no modo +% matemática. +% Também podemos entrar no modo matemática com \[\] + +\[a^2 + b^2 = c^2 \] + +Minha letra grega favorita é $\xi$. Eu também gosto da $\beta$, $\gamma$ e $\sigma$. +Eu ainda não encontrei uma letra grega que o \LaTeX \hspace{1pt} não tenha!\\ + +Operadores são parte essencial de um documento sobre matemática: +funções trigonométricas ($\sin$, $\cos$, $\tan$), +logaritmo e exponencial ($\log$, $\exp$), +limites ($\lim$), etc. +possuem comandos pré-definidos em LaTex. +Vamos escrever uma equação para ver como se faz: +$\cos(2\theta) = \cos^{2}(\theta) - \sin^{2}(\theta)$ \\ + +Frações (numerador/denominador) podem ser escritas dessa forma: + +% 10 / 7 +$$ ^{10}/_{7} $$ + +% Frações relativamente complexas podem ser escritas como +% \frac{numerator}{denominator} +$$ \frac{n!}{k!(n - k)!} $$ \\ + +Também podemos escrever equações em um ``bloco de equação''. + +% Apresenta matemática com o 'bloco' equação +\begin{equation} % entra no modo matemática + c^2 = a^2 + b^2. + \label{eq:pythagoras} % para referência + \end{equation} % toda declaração \begin precisa de uma declaração end + +Podemos então referenciar nossa nova equação! +A equação~\ref{eq:pythagoras} é também conhecida como Teorema de Pitágoras que é +também assunto da Seção~\ref{subsec:pythagoras}. Muitas coisas podem ser +rotuladas: figuras, equações, seções, etc. + +Somatórios e Integrais são escritas com os comandos sum e int: + +% Alguns compiladores LaTeX irão reclamar se existirem linhas em branco +% em um bloco de equação. +\begin{equation} + \sum_{i=0}^{5} f_{i} +\end{equation} +\begin{equation} + \int_{0}^{\infty} \mathrm{e}^{-x} \mathrm{d}x +\end{equation} + +\section{Figuras} + +Insiramos uma Figura. O local para colocar a figura pode ser difícil +de determinar. Eu tenho sempre que verificar as opções toda vez. + +\begin{figure}[H] % H aqui é uma opção para o local da figura. + \centering % centra a figura na página + % Inclui uma figura com escala de 0.8 do tamanho da página. + %\includegraphics[width=0.8\linewidth]{right-triangle.png} + % Comentado para propósitos de compilação. Por favor, use sua imaginação. + \caption{Triângulo retângulo com lados $a$, $b$, $c$} + \label{fig:right-triangle} +\end{figure} + +\subsection{Tabelas} +Também podemos incluir tabelas da mesma forma que figuras. + +\begin{table}[H] + \caption{Título para a Tabela.} + % os argumentos {} abaixo descrevem como cada linha da tabela é desenhada. + % Aqui também, Preciso ver isso. Toda. E. Cada. Vez. + \begin{tabular}{c|cc} + Número & Sobrenome & Primeiro Nome \\ % Colunas são separadas por & + \hline % uma linha horizontal + 1 & Biggus & Dickus \\ + 2 & Monty & Python + \end{tabular} +\end{table} + +\section{Fazendo o \LaTeX \hspace{1pt} não compilar algo (o código fonte)} +Digamos que precisamos incluir algum código dentro do nosso +documento \LaTeX \hspace{1pt}, para isso precisamos com o \LaTeX \hspace{1pt} +não tente interpretar esse texto e que apenas inclua ele no documento. Fazemos +isso com o bloco verbatim. + +% Existem outros pacotes (por exemplo, minty, lstlisting, etc.) +% mas verbatim é o básico +\begin{verbatim} + print("Hello World!") + a%b; % olha só! Podemos usar os sinais % no bloco verbatim. + random = 4; #decided by fair random dice roll +\end{verbatim} + +\section{Compilando} + +Imagino que agora você esteja pensando como compilar esse fantástico documento +e visualizar a gloriosa glória que é um pdf gerado por \LaTeX \hspace{1pt} pdf. +(sim, esse documento é compilável). \\ + +Finalizando o documento usando \LaTeX \hspace{1pt} consiste nos seguintes passos: + \begin{enumerate} + \item Escrever o documento em texto puro (o ``código fonte''). + \item Compilar o código fonte para gerar um pdf. + Os passos para compilar se parecem (em Linux) com: \\ + \begin{verbatim} + > pdflatex learn-latex.tex + \end{verbatim} + \end{enumerate} + +Existem editores de \LaTeX \hspace{1pt} que combinam os passos 1 e 2 no mesmo +sistema de software. Assim, você pode ver o passo 1, mas não o passo 2 por +completo. Passo 2 estará acontecendo escondido\footnote{Por exemplo, quando usar +referências (como Equação~\ref{eq:pythagoras}), pode ser necessário executar o +passo 2 várias vezes, para gerar arquivos *.aux intermediários.}. +% É assim que você adiciona notas de rodapé em seus documentos! + +Você escreve toda a informação de formatação em texto puro, no passo 1. O +momento da compilação no passo 2 é responsável por produzir o documento no +formato que você definiu no passo 1. + +\section{Links} +Nós podemos inserir links em nosso documento. Para isso nós necessitamos incluir +o pacote hyperref no preâmbulo com o comando: +\begin{verbatim} + \usepackage{hyperref} +\end{verbatim} + +Existem dois tipos principais de links: URL visíveis \\ +\url{https://learnxinyminutes.com/docs/latex/}, ou +\href{https://learnxinyminutes.com/docs/latex/}{um texto alternativo} +% Você não pode adicionar espaços extras ou símbolos especiais no texto +% alternativo, pois isso causará problemas na compilação. + +Esse pacote também produz uma lista de thumbnails no documento pdf gerado e +ativa os links na tabela de conteúdo. + +\section{End} + +Por enquanto é isso! + +% Frequentemente você precisa de uma seção de referências em seu documento. +% A forma mais fácil de configurá-la é usando uma seção de bibliografia +\begin{thebibliography}{1} + % como em outras listas, o comando \bibitem pode ser usado para itens da lista + % cada entrada pode ser citada diretamente no corpo do texto + \bibitem{latexwiki} The amazing \LaTeX \hspace{1pt} wikibook: {\em +https://en.wikibooks.org/wiki/LaTeX} + \bibitem{latextutorial} An actual tutorial: {\em http://www.latex-tutorial.com} +\end{thebibliography} + +% end the document +\end{document} +``` + +## Mais sobre LaTeX + +* The amazing LaTeX wikibook: [https://en.wikibooks.org/wiki/LaTeX](https://en.wikibooks.org/wiki/LaTeX) +* An actual tutorial: [http://www.latex-tutorial.com/](http://www.latex-tutorial.com/) diff --git a/pt-br/less-pt.html.markdown b/pt-br/less-pt.html.markdown new file mode 100644 index 00000000..f6cf2d71 --- /dev/null +++ b/pt-br/less-pt.html.markdown @@ -0,0 +1,390 @@ +--- +language: less +filename: learnless-br.less +contributors: + - ["Saravanan Ganesh", "http://srrvnn.me"] + +lang: pt-br +--- + +Less é um pré-processador de CSS, que adiciona recursos como variáveis, aninhamento, mixins e muito mais. +Less (e outros pré-processadores, como o [Sass](http://sass-lang.com/)) ajudam os desenvolvedores a escreverem código que pode ser mantido e DRY (não se repita). + +```css + + +//Comentários de linha única são removidos quando Less é compilado para CSS. + +/*Comentários de várias linhas são preservados.*/ + + + +/* Variáveis +==============================*/ + + +/* Você pode armazenar um valor de CSS (como uma cor) em uma variável. + Use o símbolo '@' para criar uma variável. */ + +@primary-color: #a3a4ff; +@secondary-color: #51527f; +@body-font: 'Roboto', sans-serif; + +/* Você pode usar as variáveis em toda a sua folha de estilo. + Agora, se você quiser alterar uma cor, só precisa fazer a alteração uma vez. */ + +body { + background-color: @primary-color; + color: @secondary-color; + font-family: @body-font; +} + +/* Isso compilará para: */ + +body { + background-color: #a3a4ff; + color: #51527F; + font-family: 'Roboto', sans-serif; +} + + +/* Isso é muito mais sustentável do que ter que mudar a cor + cada vez que aparece em toda a sua folha de estilo. */ + + + +/* Mixins +==============================*/ + + +/* Se você achar que está escrevendo o mesmo código para mais de um + elemento, você pode querer reutilizá-lo facilmente. */ + +.center { + display: block; + margin-left: auto; + margin-right: auto; + left: 0; + right: 0; +} + +/* Você pode usar o mixin simplesmente adicionando o seletor como um estilo. */ + +div { + .center; + background-color: @primary-color; +} + +/* Que compilaria para: */ + +.center { + display: block; + margin-left: auto; + margin-right: auto; + left: 0; + right: 0; +} +div { + display: block; + margin-left: auto; + margin-right: auto; + left: 0; + right: 0; + background-color: #a3a4ff; +} + +/* Você pode omitir o código mixin de ser compilado adicionando parênteses + depois do seletor. */ + +.center() { + display: block; + margin-left: auto; + margin-right: auto; + left: 0; + right: 0; +} + +div { + .center; + background-color: @primary-color; +} + +/* Que compilaria para: */ +div { + display: block; + margin-left: auto; + margin-right: auto; + left: 0; + right: 0; + background-color: #a3a4ff; +} + + + +/* Aninhamento +==============================*/ + + +/* Less permite aninhar seletores nos seletores. */ + +ul { + list-style-type: none; + margin-top: 2em; + + li { + background-color: #f00; + } +} + +/* '&' será substituído pelo seletor pai. */ +/* Você também pode aninhar pseudo-classes. */ +/* Tenha em mente que o aninhamento excessivo tornará seu código menos sustentável. + As melhores práticas recomendam não ultrapassar 3 níveis de profundidade ao aninhar. + Por exemplo: */ + +ul { + list-style-type: none; + margin-top: 2em; + + li { + background-color: red; + + &:hover { + background-color: blue; + } + + a { + color: white; + } + } +} + +/* Compila para: */ + +ul { + list-style-type: none; + margin-top: 2em; +} + +ul li { + background-color: red; +} + +ul li:hover { + background-color: blue; +} + +ul li a { + color: white; +} + + + +/* Functions +==============================*/ + + +/* Less fornece funções que podem ser usadas para realizar uma variedade de + tarefas. Considere o seguinte: */ + +/* Funções podem ser invocadas usando seu nome e passando os + argumentos requeridos. */ + +body { + width: round(10.25px); +} + +.header { + background-color: lighten(#000, 0.5); +} + +.footer { + background-color: fadeout(#000, 0.25) +} + +/* Compila para: */ + +body { + width: 10px; +} + +.header { + background-color: #010101; +} + +.footer { + background-color: rgba(0, 0, 0, 0.75); +} + +/* Você também pode definir suas próprias funções. Funções são muito semelhantes às + mixins. Ao tentar escolher entre uma função ou a um mixin, lembre-se + que mixins são melhores para gerar CSS, enquanto as funções são melhores para + lógica que pode ser usada em todo o seu código Less. Os exemplos na + seção 'Operadores Matemáticos' são candidatos ideais para se tornarem funções reutilizáveis. */ + +/* Esta função calcula a média de dois números: */ + +.average(@x, @y) { + @average-result: ((@x + @y) / 2); +} + +div { + .average(16px, 50px); // "chama" o mixin + padding: @average-result; // use seu valor de "retorno" +} + +/* Compila para: */ + +div { + padding: 33px; +} + + + +/* Estender (herança) +==============================*/ + + +/* Estender é uma maneira de compartilhar as propriedades de um seletor com outro. */ + +.display { + height: 50px; +} + +.display-success { + &:extend(.display); + border-color: #22df56; +} + +/* Compila para: */ + +.display, +.display-success { + height: 50px; +} +.display-success { + border-color: #22df56; +} + +/* Estender uma instrução CSS é preferível para criar um mixin + por causa da maneira como agrupa as classes que compartilham + o mesmo estilo base. Se isso foi feito com um mixin, as propriedades + seriam duplicadas para cada declaração que + chamou o mixin. Embora isso não afete o seu fluxo de trabalho, + adicione o inchaço desnecessário aos arquivos criados pelo compilador Less. */ + + + +/* Parciais e Importações +==============================*/ + + +/* Less permite criar arquivos parciais. Isso pode ajudar a manter o seu + código Less modularizado. Arquivos parciais convencionalmente começam com um '_', + por exemplo. _reset.less. e são importados para um arquivo less principal que recebe + o css compilado. */ + +/* Considere o seguinte CSS que vamos colocar em um arquivo chamado _reset.less */ + +html, +body, +ul, +ol { + margin: 0; + padding: 0; +} + +/* Less disponibiliza @import que podem ser usadas para importar parciais em um arquivo. + Isso difere da declaração tradicional CSS @import que faz + outra solicitação HTTP para buscar o arquivo importado. Less leva o + arquivo importado e combina com o código compilado. */ + +@import 'reset'; + +body { + font-size: 16px; + font-family: Helvetica, Arial, Sans-serif; +} + +/* Compila para: */ + +html, body, ul, ol { + margin: 0; + padding: 0; +} + +body { + font-size: 16px; + font-family: Helvetica, Arial, Sans-serif; +} + + + +/* Operações Matemáticas +==============================*/ + + +/* Less fornece os seguintes operadores: +, -, *, / e %. Estes podem + ser úteis para calcular valores diretamente nos seus arquivos Less + para usar valores que você já calculou manualmente. Abaixo está um exemplo + de como configurar um design simples de duas colunas. */ + +@content-area: 960px; +@main-content: 600px; +@sidebar-content: 300px; + +@main-size: @main-content / @content-area * 100%; +@sidebar-size: @sidebar-content / @content-area * 100%; +@gutter: 100% - (@main-size + @sidebar-size); + +body { + width: 100%; +} + +.main-content { + width: @main-size; +} + +.sidebar { + width: @sidebar-size; +} + +.gutter { + width: @gutter; +} + +/* Compila para: */ + +body { + width: 100%; +} + +.main-content { + width: 62.5%; +} + +.sidebar { + width: 31.25%; +} + +.gutter { + width: 6.25%; +} + + +``` + +## Pratique Less + +Se você quiser praticar com Less no seu navegador, confira: * [Codepen](http://codepen.io/) * [LESS2CSS](http://lesscss.org/less-preview/) + +## Compatibilidade + +Less pode ser usado em qualquer projeto, desde que você tenha um programa para compilá-lo em CSS. Você deseja verificar +se o CSS que você está usando é compatível com seus navegadores de destino. + +[QuirksMode CSS](http://www.quirksmode.org/css/) e [CanIUse](http://caniuse.com) são ótimos recursos para verificar a compatibilidade. + +## Leitura adicional +* [Documentação Oficial](http://lesscss.org/features/) +* [Less CSS - Guia do iniciante](http://www.hongkiat.com/blog/less-basic/) diff --git a/pt-br/lua-pt.html.markdown b/pt-br/lua-pt.html.markdown new file mode 100644 index 00000000..0c75da26 --- /dev/null +++ b/pt-br/lua-pt.html.markdown @@ -0,0 +1,423 @@ +--- +language: Lua +contributors: + - ["Tyler Neylon", "http://tylerneylon.com/"] +filename: learnlua.lua +translators: + - ["Iaan Mesquita", "https://github.com/ianitow"] +lang: pt-br +--- + +```lua +-- Dois hífens começam um comentário de uma linha. + +--[[ + Adicionar dois [ ] (colchetes) criam um comentário + de múltiplas linhas. +--]] + +---------------------------------------------------- +-- 1. Variáveis e fluxo de controle. +---------------------------------------------------- + +num = 42 -- Todos os números são doubles. +-- Não se preocupe, doubles de 64-bits contém 52 bits para +-- armazenar corretamente valores int; a precisão da máquina +-- não é um problema para ints que são < 52 bits. + +s = 'alternados' -- String são imutáveis, como em Python. +t = "Aspas duplas também são válidas" +u = [[ Dois colchetes + começam e terminam + strings de múltiplas linhas.]] +t = nil -- Torna t undefined(indefinido); Lua tem um Garbage Collector. + +-- Blocos são representados com palavras do/end: +while num < 50 do + num = num + 1 -- Sem operadores do tipo ++ ou += +end + +--Cláusula If : +if num > 40 then + print('over 40') +elseif s ~= 'walternate' then -- ~= signfica não é igual. + -- Para fazer checagem use == como em Python; Funciona para comparar strings também. + io.write('not over 40\n') -- Padrão para saídas. +else + -- Variáveis são globais por padrão. + thisIsGlobal = 5 -- Camel case é o comum. + + -- Como fazer variáveis locais: + local line = io.read() -- Leia a proxima linha de entrada. + + -- Para concatenação de strings use o operador .. : + print('Winter is coming, ' .. line) +end + +-- Variáveis indefinidas são do tipo nil. +-- Isso não é um erro: +foo = anUnknownVariable -- Agora foo = nil. + +aBoolValue = false + +-- Apenas nil e false são do tipo falso; 0 e '' são verdadeiros! +if not aBoolValue then print('twas false') end + +-- 'or' e 'and' são operadores lógicos. +-- Esse operador em C/JS a?b:c , em lua seria o mesmo que: +ans = aBoolValue and 'yes' or 'no' --> 'no' + +karlSum = 0 +for i = 1, 100 do -- O intervalo inclui inicio e fim. + karlSum = karlSum + i +end + +-- Use "100, 1, -1" para um intervalo que diminui: +fredSum = 0 +for j = 100, 1, -1 do fredSum = fredSum + j end + +-- Em geral, o intervalo é começo, fim[, etapas]. + +-- Outro construtor de loop: +repeat + print('A estrada do futuro.') + num = num - 1 +until num == 0 + + +---------------------------------------------------- +-- 2. Funções. +---------------------------------------------------- + +function fib(n) + if n < 2 then return 1 end + return fib(n - 2) + fib(n - 1) +end + +-- Closures e Funções anônimas são permitidas: +function adder(x) + -- O retorno da função é criado quando adder é + -- chamado, e ele sabe o valor de x: + return function (y) return x + y end +end +a1 = adder(9) +a2 = adder(36) +print(a1(16)) --> 25 +print(a2(64)) --> 100 + +-- Retornos, chamadas de funções e atribuições, todos eles trabalham +-- com listas que podem ter tamanhos incompatíveis. +-- Receptores incompatpiveis serão nil; +-- Destinos incompatíveis serão descartados. + +x, y, z = 1, 2, 3, 4 +-- Agora x = 1, y = 2, z = 3, e 4 é jogado fora. + +function bar(a, b, c) + print(a, b, c) + return 4, 8, 15, 16, 23, 42 +end + +x, y = bar('zaphod') --> imprime "zaphod nil nil" +-- Agora x = 4, y = 8, os valores 15...42 foram descartados. + +-- Funções são de primeira-classe, portanto podem ser local/global. +-- Estes exemplos são equivalentes: +function f(x) return x * x end +f = function (x) return x * x end + +-- Logo, estes são equivalentes também: +local function g(x) return math.sin(x) end +local g; g = function (x) return math.sin(x) end +-- 'local g' essa declaração de auto-referência é válida. + +-- A propósito, as funções de trigonometria trabalham em radianos. + +-- Chamadas de função com apenas um parâmetro de string não precisam de parênteses: +print 'hello' -- Funciona perfeitamente. + + +---------------------------------------------------- +-- 3. Tabelas. +---------------------------------------------------- + +-- Tabelas = A unica estrutura de dados composta em Lua; +-- elas são matrizes associativas. +-- Semelhantes aos arrays de PHP ou objetos de javascript, eles são: +-- hash-lookup(chave:valor) que também podem ser usados como listas. + +-- Usando tabelas como dicionário / mapas: + +-- Dicionários literais tem strings como chaves por padrão: +t = {key1 = 'value1', key2 = false} + +-- As chaves do tipo string podem usar notação de ponto,semelhante a javascript: +print(t.key1) -- Imprime 'value1'. +t.newKey = {} -- Adiciona um novo par chave/valor. +t.key2 = nil -- Remove key2 da tabela. + +-- Qualquer notação literal (não-nulo) pode ser uma chave: +u = {['@!#'] = 'qbert', [{}] = 1729, [6.28] = 'tau'} +print(u[6.28]) -- imprime "tau" + +-- A correspondência de chave é basicamente o valor para números +-- e strings, mas por identidade para tabelas. +a = u['@!#'] -- Agora a = 'qbert'. +b = u[{}] -- Nós esperavamso o resultado 1729, mas ele é nil: +-- b = nil já que a busca falha. Ela falha +-- porque a chave que usamos não é a mesma que o objeto +-- como aquele que usamos para guardar o valor original. Por isso +-- strings & numeros são chaves mais recomendadas. + +-- Uma chamada de função de apenas um paramêtro de tabela, não precisa de parênteses: + +function h(x) print(x.key1) end +h{key1 = 'Sonmi~451'} -- Imprime 'Sonmi~451'. + +for key, val in pairs(u) do -- Iteração de tabela. + print(key, val) +end + +-- _G é uma tabela especial que guarda tudo que é global. +print(_G['_G'] == _G) -- Imprime 'true'. + +-- Usando tabelas como listas / arrays: + +-- Listas literais com chaves int implícitas: +v = {'value1', 'value2', 1.21, 'gigawatts'} +for i = 1, #v do -- #v é o tamanho de v + print(v[i]) -- Índices começam em 1 !! MUITO LOCO! +end +-- Uma 'list' não é um tipo real. v é apenas uma tabela +-- com chaves int consecutivas, tratando ela como uma lista. + +---------------------------------------------------- +-- 3.1 Metatabelas e metamétodos. +---------------------------------------------------- + +-- Uma tabela pode ter uma metatabela que fornece à tabela +-- um compotamento de sobrecarga de operador. Depois veremos +-- como metatabelas suportam o comportamento do Javascript-prototype. + +f1 = {a = 1, b = 2} -- Representa uma fração de a/b. +f2 = {a = 2, b = 3} + +-- Isso falharia: +-- s = f1 + f2 + +metafraction = {} +function metafraction.__add(f1, f2) + sum = {} + sum.b = f1.b * f2.b + sum.a = f1.a * f2.b + f2.a * f1.b + return sum +end + +setmetatable(f1, metafraction) +setmetatable(f2, metafraction) + +s = f1 + f2 -- chama __add(f1, f2) na metatabela de f1 + +-- f1, f2 não tem chave para sua metatabela, ao contrário de +-- prototypes em javascript, então você deve recuperá-lo com +-- getmetatable(f1). A metatabela é uma tabela normal +-- com chaves que Lua reconhece, como __add. + +-- Mas a proxima linha irá falhar porque s não tem uma metatabela: +-- t = s + s +-- O padrão de Classes abaixo consertam esse problema. + +-- Uma __index em uma metatable sobrecarrega pesquisas de ponto: +defaultFavs = {animal = 'gru', food = 'donuts'} +myFavs = {food = 'pizza'} +setmetatable(myFavs, {__index = defaultFavs}) +eatenBy = myFavs.animal -- Funciona! obrigado, metatabela. + +-- As pesquisas diretas de tabela que falham tentarão pesquisar novamente usando +-- o __index da metatabela, e isso é recursivo. + +-- Um valor de __index também pode ser uma function(tbl, key) +-- para pesquisas mais personalizadas. + +-- Valores do tipo __index,add, .. são chamados de metamétodos. +-- Uma lista completa com os metamétodos. + +-- __add(a, b) para a + b +-- __sub(a, b) para a - b +-- __mul(a, b) para a * b +-- __div(a, b) para a / b +-- __mod(a, b) para a % b +-- __pow(a, b) para a ^ b +-- __unm(a) para -a +-- __concat(a, b) para a .. b +-- __len(a) para #a +-- __eq(a, b) para a == b +-- __lt(a, b) para a < b +-- __le(a, b) para a <= b +-- __index(a, b) <fn or a table> para a.b +-- __newindex(a, b, c) para a.b = c +-- __call(a, ...) para a(...) + +---------------------------------------------------- +-- 3.2 Tabelas como Classes e sua herança. +---------------------------------------------------- + +-- Classes não são disseminadas; existem maneiras diferentes +-- para fazer isso usando tabelas e metamétodos... + +-- A explicação para este exemplo está logo abaixo. + +Dog = {} -- 1. + +function Dog:new() -- 2. + newObj = {sound = 'woof'} -- 3. + self.__index = self -- 4. + return setmetatable(newObj, self) -- 5. +end + +function Dog:makeSound() -- 6. + print('I say ' .. self.sound) +end + +mrDog = Dog:new() -- 7. +mrDog:makeSound() -- 'I say woof' -- 8. + +-- 1. Dog atua como uma classe; mas na verdade, é uma tabela. +-- 2. function tablename:fn(...) é a mesma coisa que +-- function tablename.fn(self, ...) +-- O : apenas adiciona um primeiro argumento chamado self. +-- Leia 7 & 8 abaixo para ver como self obtém seu valor. +-- 3. newObj será uma instância da classe Dog. +-- 4. self = a classe que que foi instanciada. Regularmente +-- self = Dog, mas a herança pode mudar isso. +-- newObj recebe as funções de self como se tivessimos definido em ambos +-- a metatabela de newObj e self __index para self. +-- 5. Lembre-se: setmetatable retorna seu primeiro argumento definido. +-- 6. O : funciona como em 2, mas desta vez esperamos que +-- self seja uma instância já instanciada da classe. +-- 7. Igual a Dog.new(Dog), logo self = Dog no new(). +-- 8. Igual a mrDog.makeSound(mrDog); self = mrDog. + +---------------------------------------------------- + +-- Heranças exemplos: + +LoudDog = Dog:new() -- 1. + +function LoudDog:makeSound() + s = self.sound .. ' ' -- 2. + print(s .. s .. s) +end + +seymour = LoudDog:new() -- 3. +seymour:makeSound() -- 'woof woof woof' -- 4. + +-- 1. LoudDog recebe os metodos e variáveis de Dog. +-- 2. self tem uma chave 'sound' vindo de new(), veja o 3. +-- 3. Mesma coisa que LoudDog.new(LoudDog), convertido para +-- Dog.new(LoudDog) como LoudDog não tem uma chave 'new', +-- mas tem uma chave __index = Dog na sua metatabela o +-- resultado será: a metabela de seymour é a LoudDog, e +-- LoudDog.__index = LoudDog. Então seymour.key será +-- = seymour.key, LoudDog.key, Dog.key,seja qual for a primeira +-- chave fornecida. +-- 4. A chave 'makeSound' foi encontrada em LoudDog; isto +-- é a mesma coisa que LoudDog.makeSound(seymour). + +-- Se precisar de, uma subclasse de new() como uma base: +function LoudDog:new() + newObj = {} + -- define newObj + self.__index = self + return setmetatable(newObj, self) +end + +---------------------------------------------------- +-- 4. Módulos. +---------------------------------------------------- + + +--[[ Estou comentando esta seção, então o resto +-- desse script é executável. +``` + +```lua +-- Suponhamos que o arquivo mod.lua se pareça com isso: +local M = {} + +local function sayMyName() + print('Hrunkner') +end + +function M.sayHello() + print('Why hello there') + sayMyName() +end + +return M + +-- Outro arquivo pode usar as funcionalidades de mod.lua: +local mod = require('mod') -- Roda o arquivo mod.lua. + +-- require é a forma que usamos para incluir módulos. +-- require atua como: (se não for cacheado; veja abaixo) +local mod = (function () + <contents of mod.lua> +end)() +-- É como se mod.lua fosse um corpo de uma função, então +-- os locais dentro de mod.lua são invisíveis fora dele. + +-- Isso irá funcionar porque mod aqui = M dentro de mod.lua: +mod.sayHello() -- Diz olá para Hrunkner. + +-- Isso aqui é errado; sayMyName existe apenas em mod.lua: +mod.sayMyName() -- erro + +-- valores retornados de require são armazenados em cache para que um arquivo seja +-- execute no máximo uma vez, mesmo quando é exigidos várias vezes. + +-- Suponhamos que mod2.lua contém "print('Hi!')". +local a = require('mod2') -- Imprime Hi! +local b = require('mod2') -- Não imprime;pois a=b. + +-- dofile é parecido com require, porém sem cacheamento: +dofile('mod2.lua') --> Hi! +dofile('mod2.lua') --> Hi! (roda novamente) + +-- loadfile carrega um arquivo lua, porém não o executa. +f = loadfile('mod2.lua') -- Chame f() para executar. + +-- loadstring é um loadfile para strings. +g = loadstring('print(343)') -- Retorna uma função. +g() -- Imprime 343; nada foi impresso antes disso. + +--]] + +``` + +## Referências + +Fiquei bastante animado para aprender Lua pois consegui fazer jogos +com a <a href="http://love2d.org/">Love 2D engine de jogos</a>. + +Eu comecei com <a href="http://nova-fusion.com/2012/08/27/lua-for-programmers-part-1/">BlackBulletIV's para programadores LUA</a>. +Em seguida, eu li a documentação oficial <a href="https://www.lua.org/manual/5.1/pt/index.html#contents">Programando em Lua</a>. +É assim que se começa. + +Pode ser útil conferir <a href="http://lua-users.org/files/wiki_insecure/users/thomasl/luarefv51.pdf">Uma pequena referencia sobre LUA</a> em lua-users.org. + +Os principais tópicos não cobertos, são as bibliotecas padrões: + +- <a href="http://lua-users.org/wiki/StringLibraryTutorial">Biblioteca de strings</a> +- <a href="http://lua-users.org/wiki/TableLibraryTutorial">Biblioteca de tabelas</a> +- <a href="http://lua-users.org/wiki/MathLibraryTutorial">Biblioteca de matemática</a> +- <a href="http://lua-users.org/wiki/IoLibraryTutorial">Biblioteca de entrada/saída</a> +- <a href="http://lua-users.org/wiki/OsLibraryTutorial">Biblioteca do sistema operacional</a> + +A propósito, todo este arquivo é um código LUA válido, salve-o como +aprenda.lua e rode-o com "lua aprenda.lua" ! + +Este guia foi escrito pela primeira vez por tylerneylon.com, e agora +também disponível em <a href="https://gist.github.com/tylerneylon/5853042">github gist</a>. E também em português. + +Se divirta com lua diff --git a/pt-br/make-pt.html.markdown b/pt-br/make-pt.html.markdown new file mode 100644 index 00000000..cbdebde7 --- /dev/null +++ b/pt-br/make-pt.html.markdown @@ -0,0 +1,243 @@ +---
+category: tool
+tool: make
+contributors:
+ - ["Robert Steed", "https://github.com/robochat"]
+ - ["Stephan Fuhrmann", "https://github.com/sfuhrm"]
+filename: Makefile
+
+lang: pt-br
+---
+
+Um Makefile define um gráfico de regras para criar um alvo (ou alvos). Sua finalidade é fazer o mínimo de trabalho necessário para atualizar um alvo para a versão mais recente da fonte. Famosamente escrito ao longo de um fim de semana por Stuart Feldman em 1976, ainda é amplamente usada (particularmente no Unix e no Linux) apesar de muitos concorrentes e críticas.
+
+Existem muitas variedades de make na existência, no entanto, este artigo pressupõe que estamos usando o GNU make, que é o padrão no Linux.
+
+```make
+
+# Comentários podem ser escritos assim.
+
+# O arquivo deve ser nomeado Makefile e então pode ser executado como `make <alvo>`.
+# Caso contrário, nós usamos `make -f "nome-do-arquivo" <alvo>`.
+
+# Aviso - use somente TABS para identar em Makefiles, nunca espaços!
+
+#-----------------------------------------------------------------------
+# Noções básicas
+#-----------------------------------------------------------------------
+
+# Regras são do formato
+# alvo: <pré-requisito>
+# onde os pré-requisitos são opcionais.
+
+# Uma regra - esta regra só será executada se o arquivo0.txt não existir.
+arquivo0.txt:
+ echo "foo" > arquivo0.txt
+ # Mesmo os comentários nestas seções da 'receita' são passados para o shell.
+ # Experimentar `make arquivo0.txt` or simplyou simplesmente `make` - primeira regra é o padrão.
+
+# Esta regra só será executada se arquivo0.txt for mais recente que arquivo1.txt.
+arquivo1.txt: arquivo0.txt
+ cat arquivo0.txt > arquivo1.txt
+ # se as mesmas regras de citação do shell.
+ @cat arquivo0.txt >> arquivo1.txt
+ # @ pára o comando de ser ecoado para stdout.
+ -@echo 'hello'
+ # - significa que make continuará em caso de erro.
+ # Experimentar `make arquivo1.txt` na linha de comando.
+
+# Uma regra pode ter vários alvos e vários pré-requisitos
+arquivo2.txt arquivo3.txt: arquivo0.txt arquivo1.txt
+ touch arquivo2.txt
+ touch arquivo3.txt
+
+# Make vai reclamar sobre várias receitas para a mesma regra. Esvaziar
+# receitas não contam e podem ser usadas para adicionar novas dependências.
+
+#-----------------------------------------------------------------------
+# Alvos falsos
+#-----------------------------------------------------------------------
+
+# Um alvo falso. Qualquer alvo que não seja um arquivo.
+# Ele nunca será atualizado, portanto, o make sempre tentará executá-lo.
+all: maker process
+
+# Podemos declarar as coisas fora de ordem.
+maker:
+ touch ex0.txt ex1.txt
+
+# Pode evitar quebrar regras falsas quando um arquivo real tem o mesmo nome
+.PHONY: all maker process
+# Este é um alvo especial. Existem vários outros.
+
+# Uma regra com dependência de um alvo falso sempre será executada
+ex0.txt ex1.txt: maker
+
+# Alvos falsos comuns são: todos fazem instalação limpa ...
+
+#-----------------------------------------------------------------------
+# Variáveis Automáticas e Curingas
+#-----------------------------------------------------------------------
+
+process: Arquivo*.txt # Usando um curinga para corresponder nomes de arquivos
+ @echo $^ # $^ é uma variável que contém a lista de pré-requisitos
+ @echo $@ # imprime o nome do alvo
+ #(fpara várias regras alvo, $@ é o que causou a execução da regra)
+ @echo $< # o primeiro pré-requisito listado
+ @echo $? # somente as dependências que estão desatualizadas
+ @echo $+ # todas as dependências, incluindo duplicadas (ao contrário do normal)
+ #@echo $| # todos os pré-requisitos 'somente pedidos'
+
+# Mesmo se dividirmos as definições de dependência de regra, $^ vai encontrá-los
+process: ex1.txt arquivo0.txt
+# ex1.txt será encontrado, mas arquivo0.txt será desduplicado.
+
+#-----------------------------------------------------------------------
+# Padrões
+#-----------------------------------------------------------------------
+
+# Pode ensinar make a converter certos arquivos em outros arquivos.
+
+%.png: %.svg
+ inkscape --export-png $^
+
+# As regras padrões só farão qualquer coisa se decidirem criar o alvo.
+
+# Os caminhos de diretório são normalmente ignorados quando as regras de
+# padrões são correspondentes. Mas make tentará usar a regra mais
+# apropriada disponível.
+small/%.png: %.svg
+ inkscape --export-png --export-dpi 30 $^
+
+# make utilizará a última versão para uma regra de padrão que encontrar.
+%.png: %.svg
+ @echo esta regra é escolhida
+
+# No entanto, o make usará a primeira regra padrão que pode se tornar o alvo
+%.png: %.ps
+ @echo esta regra não é escolhida se *.svg and *.ps estão ambos presentes
+
+# make já tem algumas regras padrões embutidas. Por exemplo, ele sabe
+# como transformar arquivos *.c em arquivos *.o.
+
+# Makefiles antigos podem usar regras de sufixo em vez de regras padrões
+.png.ps:
+ @echo essa regra é semelhante a uma regra de padrão.
+
+# make sobre a regra de sufixo
+.SUFFIXES: .png
+
+#-----------------------------------------------------------------------
+# Variáveis
+#-----------------------------------------------------------------------
+# aka. macros
+
+# As variáveis são basicamente todos os tipos de string
+
+name = Ted
+name2="Sarah"
+
+echo:
+ @echo $(name)
+ @echo ${name2}
+ @echo $name # Isso não funcionará, tratado como $ (n)ame.
+ @echo $(name3) # Variáveis desconhecidas são tratadas como strings vazias.
+
+# Existem 4 lugares para definir variáveis.
+# Em ordem de prioridade, do maior para o menor:
+# 1: argumentos de linha de comando
+# 2: Makefile
+# 3: variáveis de ambiente do shell - faça importações automaticamente.
+# 4: make tem algumas variáveis predefinidas
+
+name4 ?= Jean
+# Somente defina a variável se a variável de ambiente ainda não estiver definida.
+
+override name5 = David
+# Pára os argumentos da linha de comando de alterar essa variável.
+
+name4 +=grey
+# Anexar valores à variável (inclui um espaço).
+
+# Valores variáveis específicos de padrões (extensão GNU).
+echo: name2 = Sara # Verdadeiro dentro da regra de correspondência
+ # e também dentro de suas recursivas dependências
+ # (exceto que ele pode quebrar quando seu gráfico ficar muito complicado!)
+
+# Algumas variáveis definidas automaticamente pelo make
+echo_inbuilt:
+ echo $(CC)
+ echo ${CXX}
+ echo $(FC)
+ echo ${CFLAGS}
+ echo $(CPPFLAGS)
+ echo ${CXXFLAGS}
+ echo $(LDFLAGS)
+ echo ${LDLIBS}
+
+#-----------------------------------------------------------------------
+# Variáveis 2
+#-----------------------------------------------------------------------
+
+# O primeiro tipo de variáveis é avaliado a cada vez que elas são usadas.
+# TIsso pode ser caro, então existe um segundo tipo de variável que é
+# avaliado apenas uma vez. (Esta é uma extensão do GNU make)
+
+var := hello
+var2 ::= $(var) hello
+#:= e ::= são equivalentes.
+
+# Essas variáveis são avaliadas procedimentalmente (na ordem em que
+# aparecem), quebrando assim o resto da línguagem!
+
+# Isso não funciona
+var3 ::= $(var4) and good luck
+var4 ::= good night
+
+#-----------------------------------------------------------------------
+# Funções
+#-----------------------------------------------------------------------
+
+# make tem muitas funções disponíveis.
+
+sourcefiles = $(wildcard *.c */*.c)
+objectfiles = $(patsubst %.c,%.o,$(sourcefiles))
+
+# O formato é $(func arg0,arg1,arg2...)
+
+# Alguns exemplos
+ls: * src/*
+ @echo $(filter %.txt, $^)
+ @echo $(notdir $^)
+ @echo $(join $(dir $^),$(notdir $^))
+
+#-----------------------------------------------------------------------
+# Diretivas
+#-----------------------------------------------------------------------
+
+# Inclua outros makefiles, úteis para código específico da plataforma
+include foo.mk
+
+sport = tennis
+# Compilação condicional
+report:
+ifeq ($(sport),tennis)
+ @echo 'game, set, match'
+else
+ @echo "They think it's all over; it is now"
+endif
+
+# Há também ifneq, ifdef, ifndef
+
+foo = true
+
+ifdef $(foo)
+bar = 'hello'
+endif
+```
+
+### More Resources
+
++ [documentação gnu make](https://www.gnu.org/software/make/manual/)
++ [tutorial de carpintaria de software](http://swcarpentry.github.io/make-novice/)
++ aprenda C da maneira mais difícil [ex2](http://c.learncodethehardway.org/book/ex2.html) [ex28](http://c.learncodethehardway.org/book/ex28.html)
diff --git a/pt-br/markdown-pt.html.markdown b/pt-br/markdown-pt.html.markdown index f22093f9..dc50cac1 100644 --- a/pt-br/markdown-pt.html.markdown +++ b/pt-br/markdown-pt.html.markdown @@ -4,6 +4,9 @@ contributors: - ["Dan Turkel", "http://danturkel.com/"] translators: - ["Miguel Araújo", "https://github.com/miguelarauj1o"] + - ["Gabriele Luz", "https://github.com/gabrieleluz"] + - ["Monique Baptista", "https://github.com/bfmonique"] + lang: pt-br filename: learnmarkdown-pt.md --- @@ -11,40 +14,50 @@ filename: learnmarkdown-pt.md Markdown foi criado por John Gruber in 2004. Originado para ser fácil de ler e escrever sintaxe que converte facilmente em HTML (hoje, suporta outros formatos também). -Dê-me feedback tanto quanto você quiser! / Sinta-se livre para a garfar (fork) e +Dê-me feedback tanto quanto você quiser! / Sinta-se livre para fazer uma bifurcação (fork) e puxar o projeto (pull request) -```markdown -<!-- Markdown é um superconjunto do HTML, de modo que qualquer arvquivo HTML é -um arquivo Markdown válido, isso significa que nós podemos usar elementos HTML +## Elementos HTML +Markdown é um superconjunto do HTML, de modo que qualquer arvquivo HTML é +um arquivo Markdown válido. +```md +<!-- Markdown é um superconjunto do HTML, de modo que qualquer arquivo HTML é +um arquivo Markdown válido. Isso significa que nós podemos usar elementos HTML em Markdown, como o elemento de comentário, e eles não serão afetados pelo analisador de remarcação. No entanto, se você criar um elemento HTML em seu arquivo Markdown, você -não pode usar sintaxe remarcação dentro desse conteúdo do elemento.--> +não pode usar sintaxe de remarcação dentro desse conteúdo do elemento.--> + +<!--A maneira como o Markdown é analisado varia de software para software. +Este guia vai tentar esclarecer quando as características são universais, ou quando eles são específicos para um determinado interpretador --> + -<!--Markdown também varia de implementação de um analisador para uma próxima. -Este guia vai tentar esclarecer quando as características são universais, ou quando eles são -específico para um determinado parser --> +## Cabeçalhos + +Você pode criar elementos HTML `<h1>` até `<h6>` facilmente antecedendo o texto +que deseja estar nesse elemento por um número de hashes (#) -<!-- Cabeçalhos --> -<!-- Você pode criar elementos HTML <h1> até <h6> facilmente antecedendo o texto -que deseja estar nesse elemento por um número de hashes (#) --> # Isto é um cabeçalho <h1> ## Isto é um cabeçalho <h2> ### Isto é um cabeçalho <h3> #### Isto é um cabeçalho <h4> ##### Isto é um cabeçalho <h5> ###### Isto é um cabeçalho <h6> +``` + +Markdown também nos fornece duas maneiras alternativas de indicar h1 e h2 -<!-- Markdown também nos fornece duas maneiras alternativas de indicar h1 e h2 --> +```md Isto é um cabeçalho h1 ====================== Isto é um cabeçalho h2 ---------------------- +``` -<!-- Estilos de texto simples --> -<!-- O texto pode ser facilmente denominado como remarcação itálico, negrito ou tachado usando --> +## Estilos de texto simples +O texto pode ser facilmente denominado como marcação itálico, negrito ou tachado usando: +```md *Este texto está em itálico* _E este também está._ @@ -54,43 +67,55 @@ __E este também está._ ***Este texto está em negrito e itálico.*** **_E este também está_** *--Danouse! Este também__* +``` -<!-- Em GitHub Flavored Markdown, que é usado para processar arquivos Markdown -GitHub, nós também temos: --> +Em GitHub Flavored Markdown, que é usado para processar arquivos Markdown +GitHub, nós também temos: +```md ~~Este texto é processado com tachado.~~ +``` -<!-- Os parágrafos estão uma ou várias linhas adjacentes de texto separadas por -uma ou múltiplas linhas em branco. --> +## Parágrafos +Os parágrafos estão uma ou várias linhas adjacentes de texto separadas por +uma ou múltiplas linhas em branco. +```md Este é um parágrafo. Eu estou digitando em um parágrafo, não é legal? -Agora, eu estou no parágrado 2. +Agora, eu estou no parágrafo 2. ... Ainda continuo no parágrafo 2! :) Eu estou no parágrafo três. +``` -<!-- Se você quiser inserir uma tag HTML <br />, você pode acabar com um parágrafo -com dois ou mais espaços e, em seguida, começar um novo parágrafo --> +Se você quiser inserir uma tag HTML `<br />`, você pode acabar com um parágrafo +com dois ou mais espaços e, em seguida, começar um novo parágrafo +```md Termino com dois espaços (destacar-me para vê-los). Há um <br /> acima de mim! +``` -<!-- Bloco de citações são fáceis e feito com o caractere >. --> +Bloco de citações são fáceis e feito com o caractere >. + +```md > Este é um bloco de citação. Você pode -> Enrolar manualmente suas linhas e colocar um `>` antes de cada linha ou você pode -> deixar suas linhas ficarem muito longas e enrolar por conta própria. Não faz diferença, +> Quebrar manualmente suas linhas e colocar um `>` antes de cada linha ou você pode +> deixar suas linhas ficarem muito longas e quebrarem por conta própria. Não faz diferença, > desde que eles começam com um `>`. + > Você também pode usar mais de um nível ->> De recuo? -> Como pura é isso? +>> De recuo? +``` -<!-- Listas --> -<!-- As listas não ordenadas podem ser feitas usando asteriscos, positivos ou hífens --> +## Listas +As listas não ordenadas podem ser feitas usando asteriscos, positivos ou hífens +```md * Item * Item * Outro item @@ -106,146 +131,202 @@ ou - Item - Item - Um último item +``` -<!-- Listas ordenadas são feitas com um número seguido por um ponto --> +Listas ordenadas são feitas com um número seguido por um ponto. +```md 1. Item um 2. Item dois -3. Tem três +3. Item três +``` -<!-- Você não tem poder para rotular os itens corretamente e a remarcação será ainda -tornar os números em ordem, mas isso pode não ser uma boa idéia --> +<!-- Você não tem poder para rotular os itens corretamente e a remarcação ainda deixará os +itens em ordem, mas isso pode não ser uma boa idéia --> + +```md 1. Item um 1. Item dois 1. Item três -<!-- (Isto é processado da mesma forma que o exemplo acima) --> +``` +(Isto é processado da mesma forma que o exemplo acima) -<!-- Você também pode usar subtítulos --> +Você também pode usar sublistas +```md 1. Item um 2. Item dois 3. Item três * Sub-item * Sub-item 4. Item quatro +``` -<!-- blocos de código --> -<!-- Você pode indicar um bloco de código (que utiliza o elemento <code>) pelo recuo -uma linha com quatro espaços ou uma guia --> +Existem também listas de tarefas. Isso cria checkboxes (caixas de seleção) de HTML +```md +As caixas abaixo sem o 'x' são checkboxes HTML desmarcadas +- [ ] Primeira tarefa a completar +- [ ] Segunda tarefa a completar +A caixa de seleção abaixo será exibida como uma checkbox HTML marcada +- [x] Essa tarefa foi completa + +``` + + +## Blocos de código +Você pode indicar um bloco de código (que utiliza o elemento `<code>`) pelo recuo +uma linha com quatro espaços ou uma guia +```md Isto é código É assim, sacou? + +``` -<!-- Você pode também re-guia (ou adicionar mais quatro espaços adicionais) para o recuo -dentro do seu código --> +Você pode também re-guia (ou adicionar mais quatro espaços adicionais) para o recuo +dentro do seu código +```md my_array.each do |item| puts item end + ``` -<!-- Código embutido pode ser criada usando o caractere de crase ` --> +Código embutido pode ser criada usando o caractere de crase `` ` `` -John não sabia nem o que o função 'goto()' fazia! - -<!-- Em GitHub Flavored Markdown, você pode usar uma sintaxe especial para o código --> +```md +John não sabia nem o que o função `goto()` fazia! +``` +Em GitHub Flavored Markdown, você pode usar uma sintaxe especial para o código +```md + ``` ruby + def foobar + puts "Hello world!" + end + ``` +``` +======= \`\`\`ruby <!-- exceto remover essas barras invertidas quando você faz isso, apenas ``` ruby! --> def foobar puts "Hello world!" end -\`\`\` <!-- Aqui também, não barras invertidas, apenas ``` --> +\`\`\` <!-- Aqui também, não use barras invertidas, apenas ``` --> -<-- O texto acima não requer recuo, mas o GitHub vai usar a sintaxe -destacando do idioma que você especificar após a ``` --> +O texto acima não requer recuo, além disso o GitHub vai usar a sintaxe highlight da linguagem que você especificar após a \`\`\`. -<!-- Regra Horizontal (<hr />) --> -<!-- Regras horizontais são facilmente adicionados com três ou mais asteriscos ou hífens, -com ou sem espaços. --> +## Linha Horizontal +Linhas horizontais são facilmente adicionados com três ou mais asteriscos ou hífens, +com ou sem espaços. +```md *** --- - - - **************** +``` -<!-- Links --> -<!-- Uma das melhores coisas sobre a remarcação é o quão fácil é fazer ligações. Colocar -o texto a ser exibido entre parênteses rígidos [] seguido pela url em parênteses () --> +## Links +Uma das melhores coisas sobre a marcação é o quão fácil é fazer ligações. Colocar +o texto a ser exibido entre parênteses rígidos [] seguido pela url em parênteses () +```md [Click aqui!](http://test.com/) +``` -<!-- Você também pode adicionar um título link usando aspas dentro dos parênteses --> +Você também pode adicionar um título link usando aspas dentro dos parênteses +```md [Click aqui!](http://test.com/ "Link para Test.com") +``` -<!-- Caminhos relativos funcionam também. --> +Caminhos relativos funcionam também. +```md [Ir para música](/música/). +``` -<!-- Markdown também suporta ligações de estilo de referência --> +Markdown também suporta ligações de estilo de referência +```md [Clique neste link] [link1] para mais informações sobre isso! [Além disso, verifique este link] [foobar] se você quiser. [link1]: http://test.com/ "Legal!" [foobar]: http://foobar.biz/ "OK!" +``` -<!-- O título também pode estar entre aspas simples ou entre parênteses, ou omitido +O título também pode estar entre aspas simples ou entre parênteses, ou omitido inteiramente. As referências podem estar em qualquer lugar no documento e os IDs de referência -pode ser qualquer um, desde que eles são únicos. --> +pode ser qualquer um, desde que eles são únicos. -<!-- Existe também o "nomear implícita", que permite que você use o texto do link como o id --> +Existe também a "nomeação implicita", que permite que você use o texto do link como o id +```md [Este] [] é um link. [este]: http://thisisalink.com/ +``` -<!-- Mas não são usados normalmente--> +Mas não são usados normalmente -<!-- Imagens --> -<!-- As imagens são feitas da mesma forma que as ligações, mas com um ponto de exclamação na frente! --> +## Imagens +As imagens são feitas da mesma forma que as ligações, mas com um ponto de exclamação na frente! +```md ![Este é pairar-texto (texto alternativo) para minha imagem](http://imgur.com/myimage.jpg "Um título opcional") +``` -<!-- E estilo de referência funciona como esperado --> +E estilo de referência funciona como esperado +```md ![Este é o pairar-texto.][Myimage] [myimage]: relative/urls/legal/image.jpg "se você precisa de um título, é aqui" +``` -<!-- Miscelânea --> -<!-- Auto-links --> +## Miscelânea +### Auto-links +```md <http://testwebsite.com/> é equivalente a [http://testwebsite.com/](http://testwebsite.com/) +``` -<!-- Auto-links para e-mails --> +### Auto-links para e-mails +```md <foo@bar.com> +``` -<!-- Escapando caracteres --> +### Escapando caracteres Quero digitar * Este texto entre asteriscos *, mas eu não quero que ele seja em itálico, então eu faço o seguinte: \*Este texto entre asteriscos \*. -<!-- Tabelas --> -<!-- Tabelas estão disponíveis apenas no GitHub Flavored Markdown e são ligeiramente -complicadas, mas se você realmente quer: --> +### Tabelas +Tabelas estão disponíveis apenas no GitHub Flavored Markdown e são ligeiramente +complicadas, mas se você realmente quer: +```md | Col1 | Col2 | Col3 | | :----------- | :------: | ------------: | | esquerda-alin| Centrado | direita-alinh | | blah | blah | blah | +``` -<!-- Ou, para os mesmos resultados --> +Ou, para os mesmos resultados +```md Col 1 | Col2 | Col3 :-- | :-: | --: Ugh isso é tão feio | faça isto | parar +``` -<!-- O fim! --> +Fim! -``` +--- Para mais informações, confira o post oficial de John Gruber de sintaxe [aqui](http://daringfireball.net/projects/markdown/syntax) e de Adam Pritchard grande cheatsheet [aqui](https://github.com/adam-p/markdown-here/wiki/Markdown-Cheatsheet). diff --git a/pt-br/matlab-pt.html.markdown b/pt-br/matlab-pt.html.markdown index eb660d4c..fae17bca 100644 --- a/pt-br/matlab-pt.html.markdown +++ b/pt-br/matlab-pt.html.markdown @@ -206,8 +206,7 @@ size(A) % Resposta = 3 3 A(1, :) =[] % Remove a primeira linha da matriz A(:, 1) =[] % Remove a primeira coluna da matriz -transpose(A) % Transposta a matriz, que é o mesmo de: -A one +transpose(A) % Transposta a matriz, que é o mesmo de: A.' ctranspose(A) % Transposta a matriz % (a transposta, seguida pelo conjugado complexo de cada elemento) @@ -357,7 +356,7 @@ disp(a) % Imprime o valor da variável a disp('Olá Mundo') % Imprime a string fprintf % Imprime na janela de comandos com mais controle -% Estruturas Condicionais (os parênteses são opicionais, porém uma boa prática) +% Estruturas Condicionais (os parênteses são opcionais, porém uma boa prática) if (a > 15) disp('Maior que 15') elseif (a == 23) diff --git a/pt-br/paren-pt.html.markdown b/pt-br/paren-pt.html.markdown index 464a69d2..92414ba3 100644 --- a/pt-br/paren-pt.html.markdown +++ b/pt-br/paren-pt.html.markdown @@ -182,8 +182,8 @@ a ; => (3 2) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; Macros lhe permitem estender a sintaxe da linguagem. -;; Os macros no Paren são fáceis. -;; Na verdade, (defn) é um macro. +;; As macros no Paren são fáceis. +;; Na verdade, (defn) é uma macro. (defmacro setfn (nome ...) (set nome (fn ...))) (defmacro defn (nome ...) (def nome (fn ...))) @@ -191,6 +191,6 @@ a ; => (3 2) (defmacro infix (a op ...) (op a ...)) (infix 1 + 2 (infix 3 * 4)) ; => 15 -;; Macros não são higiênicos, você pode sobrescrever as variáveis já existentes! -;; Eles são transformações de códigos. +;; Macros não são higiênicas, você pode sobrescrever as variáveis já existentes! +;; Elas são transformações de códigos. ``` diff --git a/pt-br/pascal-pt.html.markdown b/pt-br/pascal-pt.html.markdown new file mode 100644 index 00000000..72302695 --- /dev/null +++ b/pt-br/pascal-pt.html.markdown @@ -0,0 +1,254 @@ +--- +language: Pascal +filename: learnpascal-pt.pas +contributors: + - ["Ganesha Danu", "https://github.com/blinfoldking"] + - ["Keith Miyake", "https//github.com/kaymmm"] + - ["Raul Almeida", "https://github.com/almeidaraul"] +translators: + - ["Raul Almeida", "https://github.com/almeidaraul"] +lang: pt-br +--- + + +>Pascal é uma linguagem de programação estruturada, que recebeu este nome em homenagem ao matemático e físico Blaise Pascal. Foi criada em 1970 pelo suíço Niklaus Wirth,tendo em mente encorajar o uso de código estruturado. +fonte : [wikipédia](https://pt.wikipedia.org/wiki/Pascal_(linguagem_de_programa%C3%A7%C3%A3o)) + + + +Para compilar e executar um programa em Pascal, você pode usar o freepascal, +um compilador gratuito. [Faça o download aqui](https://www.freepascal.org/) + +```pascal +//Corpo de um programa em Pascal +//isso é um comentário +{ + isso também é um comentário, + mas com várias linhas +} + +//cabeçalho do programa +PROGRAM aprendendo_pascal; //<-- não esqueça o ponto e vírgula. O nome do +programa deve começar com uma letra. + +CONST + { + aqui você declara valores constantes + } +TYPE + { + aqui você declara tipos não nativos + } +VAR + { + aqui você declara variáveis + } + +//programa de fato +BEGIN + 80 + aqui ficam todas as instruções que não pertencem nem a funções + nem a procedimentos + + blocos de código começam com BEGIN e terminam com END + (como as chaves em C) + } +END. //o "end" no final do programa requer um ponto final. +``` + +```pascal +//formas de declarar uma variável +VAR a:INTEGER; +VAR b:INTEGER; + +VAR + a : INTEGER; + b : INTEGER; + +VAR a,b : INTEGER; +``` + +```pascal +PROGRAM Learn_More; +//agora, mais sobre tipos de dados e operações + +CONST + PI = 3.141592654; + GNU = 'GNU''s Not Unix'; + { a convenção é usar caixa alta para constantes + + constantes têm valores fixos que só podem ser alterados + antes da compilação + + constantes podem ser de qualquer tipo nativo (integer, real, boolean, + char, string) + +TYPE + vet_char : array [0..255] of CHAR; + // isso declara um novo tipo de variável, vet_char, com 256 caracteres + vet_multd : array of array of INTEGER; + // vetores de vetores são vetores multidimensionais + // use vetores de tamanho 0 (daí, usa-se alocação dinâmica) + // vetores do tipo vet_multd são de duas dimensões + +//declarando variáveis +VAR + int, c, d : INTEGER; + // três variáveis que guardam valores inteiros + // inteiros têm 16 bits (vão de -32768 a 32767) + r : REAL; + // uma variável que guarda um valor real + // reais vão de 3.4E-38 a 3.4E38 + bool : BOOLEAN; + // uma variável que guarda um valor booleano (verdadeiro ou falso) + ch : CHAR; + // uma variável que guarda um caractere + // caracteres têm 8 bits + str : STRING; + // STRING não é um tipo padrão, mas vem na maioria dos compiladores + // string é um vetor de caracteres com tamanho padrão de 255 elementos + s : STRING[50]; + // especificar o tamanho de uma string assim otimiza o uso de memória + my_str: vet_char; + // aqui, uma variável de um tipo personalizado declarado acima + my_2d : vet_multd; + // defina o tamanho de vetores dinâmicos antes de usá-los + +// outros tipos de dados (pascal é uma linguagem fortemente tipada) + + // tipos adicionais de inteiros + b : BYTE; // faixa [0..255] + shi : SHORTINT; // faixa [-128..127] + smi : SMALLINT; // faixa [-32,768..32,767] (inteiro padrão) + w : WORD; // faixa [0..65,535] + li : LONGINT; // faixa [-2,147,483,648..2,147,483,647] + lw : LONGWORD; // faixa [0..4,294,967,295] + c : CARDINAL; // longword + i64 : INT64; // faixa [-9223372036854775808..9223372036854775807] + qw : QWORD; // faixa [0..18,446,744,073,709,551,615] + + // tipos adicionais de reais + rr : REAL; // faixa depende da plataforma (8 bits, 16 bits, etc) + rs : SINGLE; // faixa [1.5E-45..3.4E38] + rd : DOUBLE; // faixa [5.0E-324 .. 1.7E308] + re : EXTENDED; // faixa [1.9E-4932..1.1E4932] + rc : COMP; // faixa [-2E64+1 .. 2E63-1] + +BEGIN + int := 1;// usa-se := para atribuir valores a variáveis + r := 3.14; + ch := 'a'; + str := 'apple'; + bool := true; + //pascal não é case-sensitive (não diferencia maiúsculas de minúsculas) + // uma opção de organização é usar maiúsculas para termos da linguagem + // (BEGIN, END, INTEGER, etc) e constantes + // aritmética + int := 1 + 1; // int deixa de ser 1 e passa a ser 2 + int := int + 1; // int = 2 + 1 = 3; + int := 4 DIV 2; //int = 2 (DIV é uma divisão inteira - ignora o resto) + int := 3 DIV 2; //int = 1 + int := 1 DIV 2; //int = 0 + + bool := true OR false; // bool = true + bool := false AND true; // bool = false + bool := true XOR true; // bool = false + + r := 3 / 2; // usa-se a "/" para divisões entre inteiros + r := int; // um real pode receber um valor inteiro (mas não o contrário) + + c := str[1]; //acessando elementos de um vetor: vetor[índice do elemento] + str := 'hello' + 'world'; //concatenação de strings + + my_str[0] := 'a'; { só se pode atribuir valores a vetores elemento + por elemento (não o vetor inteiro de uma vez) } + + // LAÇOS + WHILE (ch != 'a') DO + BEGIN + writeln('ch é diferente de a'); + IF (ch = 'c') THEN + writeln('ch é igual a c'); + END; + + SETLENGTH(my_2d,10,10); + // inicialização de um vetor com alocação dinâmica; my_2d vira um 10x10 + FOR c := 0 to 9 DO + { vetores começam em 0 e terminam em tamanho-1 + (exceto se, declarando o tipo, forem especificados valores diferentes) } + FOR d := 0 to 9 DO + // a variável usada em um laço FOR deve ter sido declarada no cabeçalho + my_2d[c,d] := c * d; + // acessam-se elementos de vetores multidimensionais com [d1, d2, d3...] + + +END. +``` + +```pascal +PROGRAM programacao_com_funcoes; + +VAR + i, inutil : INTEGER; + +{ OBS: diferença entre procedimento e função + função: realiza operações e retorna valor + procedimento: só realiza operações +} +//declarando e descrevendo uma função +FUNCTION fatorial_recursiva(CONST a: INTEGER) : INTEGER; +{ calcula a! recursivamente } + +// pode-se declarar variáveis locais para funções e procedimentos +// exemplo: +// VAR +// local_a : INTEGER; + +BEGIN + { O bloco ELSE só funciona se não houver ponto e vírgula no bloco do IF + exemplo: + IF a THEN + writeln('a'); + ELSE + writeln('b'); + Isso não permitiria que o programa compilasse } + + IF a >= 1 THEN + // o valor de retorno é atribuído como se a função fosse uma variável + fatorial_recursiva := a * fatorial_recursiva(a-1) + ELSE + fatorial_recursiva := 1; +END; // o END de funções e procedimentos recebe ponto e vírgula + +//declarando e descrevendo um procedimento +PROCEDURE salvainteiro(VAR i : INTEGER; inutil : INTEGER); +{ recebe entrada do usuário e salva na variável i + passagem de valor: + + POR REFERÊNCIA - "VAR i: integer"; implica que alterações na variável i + dentro da função são guardadas para o escopo de todo o programa + + POR VALOR - "inutil: integer"; implica que o valor do argumento é copiado + e alterações na variável inutil não são guardadas +} + +BEGIN + WRITE('Insira um inteiro: '); //escreve sem quebrar linha + READLN(i); //lê i com quebra de linha + inutil := 4; // inutil não terá seu valor alterado fora do procedimento. +END; + +BEGIN // programa principal + inutil := 3; + salvainteiro(i, inutil); + + // escrevendo i! + WRITELN(i, '! = ', factorial_recursion(i)); // escreve e quebra linha + // valores numéricos são automaticamente convertidos para texto na escrita + + // escrever valor de inutil (sempre 3, já que salvainteiro não a altera) + WRITELN('inutil = ', inutil); +END. + +``` + diff --git a/pt-br/perl-pt.html.markdown b/pt-br/perl-pt.html.markdown index cc07a2ec..55a10626 100644 --- a/pt-br/perl-pt.html.markdown +++ b/pt-br/perl-pt.html.markdown @@ -10,9 +10,9 @@ translators: lang: pt-br --- -Perl 5 é, uma linguagem de programação altamente capaz, rica em recursos, com mais de 25 anos de desenvolvimento. +Perl é, uma linguagem de programação altamente capaz, rica em recursos, com mais de 25 anos de desenvolvimento. -Perl 5 roda em mais de 100 plataformas, de portáteis a mainframes e é adequada tanto para prototipagem rápida, quanto em projetos de desenvolvimento em grande escala. +Perl roda em mais de 100 plataformas, de portáteis a mainframes e é adequada tanto para prototipagem rápida, quanto em projetos de desenvolvimento em grande escala. ```perl # Comentários de uma linha começam com um sinal de número. @@ -21,7 +21,7 @@ Perl 5 roda em mais de 100 plataformas, de portáteis a mainframes e é adequada # Variáveis iniciam com um sigilo, que é um símbolo que mostra o tipo. # Um nome de variável válido começa com uma letra ou sublinhado, -# seguido por qualquer número de letras, números ou sublinhados. +# seguido por qualquer quantidade de letras, números ou sublinhados. ### Perl has three main variable types: $scalar, @array, e %hash. @@ -52,10 +52,10 @@ my %fruta_cor = ( banana => "amarelo", ); -# Scalars, arrays and hashes são documentados mais profundamentes em perldata. +# Scalars, arrays and hashes são documentados mais profundamente em perldata. # (perldoc perldata). -# Mais tipos de dados complexos podem ser construídas utilizando referências, +# Mais tipos de dados complexos podem ser construídos utilizando referências, # o que permite que você crie listas e hashes dentro de listas e hashes. #### Condicionais e construtores de iteração diff --git a/pt-br/php-pt.html.markdown b/pt-br/php-pt.html.markdown index 8a1c956e..e55f1100 100644 --- a/pt-br/php-pt.html.markdown +++ b/pt-br/php-pt.html.markdown @@ -20,7 +20,7 @@ Este documento descreve PHP 5+. // Duas barras iniciam o comentário de uma linha. -# O hash (aka pound symbol) também inicia, mas // é mais comum. +# O hash (conhecido como "pound symbol") também inicia, mas // é mais comum. /* O texto envolto por barra-asterisco e asterisco-barra diff --git a/pt-br/pyqt-pt.html.markdown b/pt-br/pyqt-pt.html.markdown new file mode 100644 index 00000000..40fe82d5 --- /dev/null +++ b/pt-br/pyqt-pt.html.markdown @@ -0,0 +1,92 @@ +--- +category: tool +tool: PyQT +filename: learnpyqt-pt.py +contributors: + - ["Nathan Hughes", "https://github.com/sirsharpest"] +translators: + - ["Lucas Pugliesi", "https://github.com/fplucas"] +lang: pt-br +--- + +**Qt** é amplamente conhecido como um framework para desenvolvimento de +software multi-plataforma que pode rodar em várias outras plataformas de +softwares e hardwares com pouca ou nenhuma alteração no código, enquanto mantém +o poder e a velocidade de uma aplicação nativa. Embora o **Qt** tenha sido +originalmente escrito em *C++*. + + +Essa é uma adaptação de uma introdução ao QT em C++ por +[Aleksey Kholovchuk](https://github.com/vortexxx192), alguns dos exemplos de +código podem resultar na mesma funcionalidade que essa versão, apenas usando +o pyqt! + +```python +import sys +from PyQt4 import QtGui + +def window(): + # Cria um objeto para a aplicação + app = QtGui.QApplication(sys.argv) + # Cria um widget onde o nosso label será inserido + w = QtGui.QWidget() + # Adiciona um label ao widget + b = QtGui.QLabel(w) + # Informa algum texto ao label + b.setText("Hello World!") + # Define os tamanhos e posições dos objetos + w.setGeometry(100, 100, 200, 50) + b.move(50, 20) + # Define o título da janela + w.setWindowTitle("PyQt") + # Exibe a janela + w.show() + # Executa tudo o que foi pedido, apenas uma vez + sys.exit(app.exec_()) + +if __name__ == '__main__': + window() + +``` + +Para utilizar mais funcionalidades no **pyqt** veremos a construção de alguns +outros elementos. +Aqui mostraremos como criar uma janela popup, muito útil para perguntar ao +usuário qual decisão tomar ou exibir alguma informação. + +```Python +import sys +from PyQt4.QtGui import * +from PyQt4.QtCore import * + + +def window(): + app = QApplication(sys.argv) + w = QWidget() + # Cria um botão e o anexa ao widget w + b = QPushButton(w) + b.setText("Press me") + b.move(50, 50) + # Informa b a chamar essa função quando for clicado + # observe que a função chamada não necessita de "()" + b.clicked.connect(showdialog) + w.setWindowTitle("PyQt Dialog") + w.show() + sys.exit(app.exec_()) + +# Essa função deve criar uma janela de diálogo com um botão, +# aguarda ser clicado e encerra o programa +def showdialog(): + d = QDialog() + b1 = QPushButton("ok", d) + b1.move(50, 50) + d.setWindowTitle("Dialog") + # Essa modalidade define que o popup deve bloquear as outras janelas quando ativo + d.setWindowModality(Qt.ApplicationModal) + # Ao ser clicado deve encerrar o processo + b1.clicked.connect(sys.exit) + d.exec_() + +if __name__ == '__main__': + window() +``` diff --git a/pt-br/python-pt.html.markdown b/pt-br/python-pt.html.markdown index 5afd46d0..3f9c54c1 100644 --- a/pt-br/python-pt.html.markdown +++ b/pt-br/python-pt.html.markdown @@ -1,29 +1,36 @@ --- -language: python +language: Python contributors: - - ["Louie Dinh", "http://ldinh.ca"] + - ["Louie Dinh", "http://pythonpracticeprojects.com"] + - ["Steven Basart", "http://github.com/xksteven"] + - ["Andre Polykanine", "https://github.com/Oire"] + - ["Zachary Ferguson", "http://github.com/zfergus2"] translators: - - ["Vilson Vieira", "http://automata.cc"] + - ["Paulo Henrique Rodrigues Pinheiro", "http://www.sysincloud.it"] + - ["Monique Baptista", "https://github.com/bfmonique"] lang: pt-br filename: learnpython-pt.py --- -Python foi criado por Guido Van Rossum no começo dos anos 90. Atualmente é uma -das linguagens de programação mais populares. Eu me apaixonei por Python, por -sua clareza de sintaxe. É basicamente pseudocódigo executável. +Python foi criada por Guido Van Rossum nos anos 1990. Ela é atualmente uma +das linguagens mais populares existentes. Eu me apaixonei por +Python por sua clareza sintática. É praticamente pseudocódigo executável. -Comentários serão muito apreciados! Você pode me contactar em -[@louiedinh](http://twitter.com/louiedinh) ou louiedinh [arroba] -[serviço de email do google] +Opniões são muito bem vindas. Você pode encontrar-me em +[@louiedinh](http://twitter.com/louiedinh) ou louiedinh [em] +[serviço de e-mail do google]. -Nota: Este artigo usa Python 2.7 especificamente, mas deveria ser aplicável a -qualquer Python 2.x. Logo haverá uma versão abordando Python 3! +Observação: Este artigo trata de Python 3 especificamente. Verifique +[aqui](http://learnxinyminutes.com/docs/pt-br/python-pt/) se você pretende +aprender o velho Python 2.7. ```python -# Comentários de uma linha começam com cerquilha (ou sustenido) + +# Comentários em uma única linha começam com uma cerquilha (também conhecido por sustenido). + """ Strings de várias linhas podem ser escritas usando três ", e são comumente usadas - como comentários + como comentários. """ #################################################### @@ -31,287 +38,385 @@ qualquer Python 2.x. Logo haverá uma versão abordando Python 3! #################################################### # Você usa números normalmente -3 #=> 3 - -# Operadores matemáticos são aqueles que você já está acostumado -1 + 1 #=> 2 -8 - 1 #=> 7 -10 * 2 #=> 20 -35 / 5 #=> 7 - -# A divisão é um pouco estranha. A divisão de números inteiros arredonda -# para baixo o resultado, automaticamente -5 / 2 #=> 2 +3 # => 3 -# Para concertar a divisão, precisamos aprender sobre números de ponto -# flutuante (conhecidos como 'float'). -2.0 # Isso é um 'float' -11.0 / 4.0 #=> 2.75 ahhh... muito melhor +# Matemática é como você espera que seja +1 + 1 # => 2 +8 - 1 # => 7 +10 * 2 # => 20 -# Forçamos a precedência de operadores usando parênteses -(1 + 3) * 2 #=> 8 +# Números são inteiros por padrão, exceto na divisão, que retorna número +# de ponto flutuante (float). +35 / 5 # => 7.0 -# Valores booleanos (ou 'boolean') são também tipos primitivos -True -False +# O resultado da divisão inteira arredonda para baixo tanto para números +# positivos como para negativos. +5 // 3 # => 1 +5.0 // 3.0 # => 1.0 # funciona em float também +-5 // 3 # => -2 +-5.0 // 3.0 # => -2.0 -# Negamos usando 'not' -not True #=> False -not False #=> True +# Quando você usa um float, o resultado é float. +3 * 2.0 # => 6.0 -# Testamos igualdade usando '==' -1 == 1 #=> True -2 == 1 #=> False +# operador módulo +7 % 3 # => 1 -# E desigualdade com '!=' -1 != 1 #=> False -2 != 1 #=> True - -# Mais comparações -1 < 10 #=> True -1 > 10 #=> False -2 <= 2 #=> True -2 >= 2 #=> True +# Exponenciação (x**y, x elevado à potência y) +2**4 # => 16 -# As comparações podem ser encadeadas! -1 < 2 < 3 #=> True -2 < 3 < 2 #=> False +# Determine a precedência usando parênteses +(1 + 3) * 2 # => 8 -# Strings são criadas com " ou ' -"Isso é uma string." -'Isso também é uma string.' +# Valores lógicos são primitivos (Atenção à primeira letra maiúscula) +True +False -# Strings podem ser somadas (ou melhor, concatenadas)! -"Olá " + "mundo!" #=> "Olá mundo!" +# negação lógica com not +not True # => False +not False # => True -# Uma string pode ser tratada como uma lista de caracteres -"Esta é uma string"[0] #=> 'E' +# Operadores lógicos +# Observe que "and" e "or" são sensíveis a maiúsculas e minúsculas +True and False # => False +False or True # => True -# O caractere % pode ser usado para formatar strings, desta forma: -"%s podem ser %s" % ("strings", "interpoladas") +# Observe a utilização de operadores lógicos com números inteiros +0 and 2 # => 0 +-5 or 0 # => -5 +0 == False # => True +2 == True # => False +1 == True # => True -# Um jeito novo de formatar strings é usando o método 'format'. -# Esse método é o jeito mais usado -"{0} podem ser {1}".format("strings", "formatadas") -# Você pode usar palavras-chave (ou 'keywords') se você não quiser contar. -"{nome} quer comer {comida}".format(nome="João", comida="lasanha") +# Igualdade é == +1 == 1 # => True +2 == 1 # => False -# 'None' é um objeto -None #=> None +# Diferença é != +1 != 1 # => False +2 != 1 # => True -# Não use o operador de igualdade `==` para comparar objetos com 'None' -# Ao invés disso, use `is` -"etc" is None #=> False -None is None #=> True +# Mais comparações +1 < 10 # => True +1 > 10 # => False +2 <= 2 # => True +2 >= 2 # => True + +# Comparações podem ser agrupadas +1 < 2 < 3 # => True +2 < 3 < 2 # => False + +# 'is' verifica se duas variáveis representam o mesmo endereço +# na memória; '==' verifica se duas variáveis têm o mesmo valor +a = [1, 2, 3, 4] # Referência a uma nova lista, [1, 2, 3, 4] +b = a # b referencia o que está referenciado por a +b is a # => True, a e b referenciam o mesmo objeto +b == a # => True, objetos a e b tem o mesmo conteúdo +b = [1, 2, 3, 4] # Referência a uma nova lista, [1, 2, 3, 4] +b is a # => False, a e b não referenciam o mesmo objeto +b == a # => True, objetos a e b tem o mesmo conteúdo -# O operador 'is' teste a identidade de um objeto. Isso não é -# muito útil quando estamos lidando com valores primitivos, mas é -# muito útil quando lidamos com objetos. +# Strings são criadas com " ou ' +"Isto é uma string." +'Isto também é uma string.' -# None, 0, e strings/listas vazias são todas interpretadas como 'False'. -# Todos os outros valores são 'True' -0 == False #=> True -"" == False #=> True +# Strings também podem ser somadas! Mas tente não fazer isso. +"Olá " + "mundo!" # => "Olá mundo!" +# Strings podem ser somadas sem usar o '+' +"Olá " "mundo!" # => "Olá mundo!" +# Uma string pode ser manipulada como se fosse uma lista de caracteres +"Isso é uma string"[0] # => 'I' -#################################################### -## 2. Variáveis e Coleções -#################################################### +# .format pode ser usado para formatar strings, dessa forma: +"{} podem ser {}".format("Strings", "interpoladas") # => "Strings podem ser interpoladas" -# Imprimir na tela é muito fácil -print "Eu sou o Python. Prazer em te conhecer!" +# Você pode repetir os argumentos para digitar menos. +"Seja ágil {0}, seja rápido {0}, salte sobre o {1} {0}".format("Jack", "castiçal") +# => "Seja ágil Jack, seja rápido Jack, salte sobre o castiçal Jack." +# Você pode usar palavras-chave se quiser contar. +"{nome} quer comer {comida}".format(nome="Beto", comida="lasanha") # => "Beto quer comer lasanha" -# Nós não precisamos declarar variáveis antes de usá-las, basta usar! -alguma_variavel = 5 # A convenção é usar caixa_baixa_com_sobrescritos -alguma_variavel #=> 5 +# Se você precisa executar seu código Python3 com um interpretador Python 2.5 ou acima, você pode usar a velha forma para formatação de texto: +"%s podem ser %s da forma %s" % ("Strings", "interpoladas", "antiga") # => "Strings podem ser interpoladas da forma antiga" -# Acessar uma variável que não teve nenhum valor atribuído anteriormente é -# uma exceção. -# Veja a seção 'Controle' para aprender mais sobre tratamento de exceção. -outra_variavel # Gera uma exceção de erro de nome -# 'if' pode ser usado como uma expressão -"uepa!" if 3 > 2 else 2 #=> "uepa!" +# None é um objeto +None # => None -# Listas armazenam sequências de elementos -lista = [] -# Você pode inicializar uma lista com valores -outra_lista = [4, 5, 6] +# Não use o operador de igualdade "==" para comparar objetos com None +# Use "is" para isso. Ele checará pela identidade dos objetos. +"etc" is None # => False +None is None # => True -# Adicione elementos no final da lista usando 'append' -lista.append(1) # lista é agora [1] -lista.append(2) # lista é agora [1, 2] -lista.append(4) # lista é agora [1, 2, 4] -lista.append(3) # lista é agora [1, 2, 4, 3] -# Remova elementos do fim da lista usando 'pop' -lista.pop() #=> 3 e lista é agora [1, 2, 4] -# Vamos adicionar o elemento novamente -lista.append(3) # lista agora é [1, 2, 4, 3] novamente. +# None, 0, e strings/listas/dicionários vazios todos retornam False. +# Qualquer outra coisa retorna True +bool(0) # => False +bool("") # => False +bool([]) # => False +bool({}) # => False -# Acesse elementos de uma lista através de seu índices -lista[0] #=> 1 -# Acesse o último elemento com índice negativo! -lista[-1] #=> 3 -# Tentar acessar um elemento fora dos limites da lista gera uma exceção -# do tipo 'IndexError' -lista[4] # Gera uma exceção 'IndexError' - -# Você pode acessar vários elementos ao mesmo tempo usando a sintaxe de -# limites -# (Para quem gosta de matemática, isso é um limite fechado/aberto) -lista[1:3] #=> [2, 4] -# Você pode omitir o fim se quiser os elementos até o final da lista -lista[2:] #=> [4, 3] -# O mesmo para o início -lista[:3] #=> [1, 2, 4] +#################################################### +## 2. Variáveis e coleções +#################################################### -# Remova um elemento qualquer de uma lista usando 'del' -del lista[2] # lista agora é [1, 2, 3] +# Python tem uma função print +print("Eu sou o Python. Prazer em conhecer!") # => Eu sou o Python. Prazer em conhecer! + +# Por padrão a função print também imprime o caractere de nova linha ao final. +# Use o argumento opcional end para mudar o caractere final. +print("Olá, Mundo", end="!") # => Olá, Mundo! + +# Forma simples para capturar dados de entrada via console +input_string_var = input("Digite alguma coisa: ") # Retorna o que foi digitado em uma string +# Observação: Em versões antigas do Python, o método input() era chamado raw_input() + +# Não é necessário declarar variáveis antes de iniciá-las +# É uma convenção usar letras_minúsculas_com_sublinhados +alguma_variavel = 5 +alguma_variavel # => 5 + +# Acessar uma variável que não tenha sido inicializada gera uma exceção. +# Veja Controle de Fluxo para aprender mais sobre tratamento de exceções. +alguma_variavel_nao_inicializada # Gera a exceção NameError + +# Listas armazenam sequências +li = [] +# Você pode iniciar uma lista com valores +outra_li = [4, 5, 6] + +# Adicione conteúdo ao fim da lista com append +li.append(1) # li agora é [1] +li.append(2) # li agora é [1, 2] +li.append(4) # li agora é [1, 2, 4] +li.append(3) # li agora é [1, 2, 4, 3] +# Remova do final da lista com pop +li.pop() # => 3 e agora li é [1, 2, 4] +# Vamos colocá-lo lá novamente! +li.append(3) # li agora é [1, 2, 4, 3] novamente. + +# Acesse uma lista da mesma forma que você faz com um array +li[0] # => 1 +# Acessando o último elemento +li[-1] # => 3 + +# Acessar além dos limites gera um IndexError +li[4] # Gera o IndexError + +# Você pode acessar vários elementos com a sintaxe de limites +# Inclusivo para o primeiro termo, exclusivo para o segundo +li[1:3] # => [2, 4] +# Omitindo o final +li[2:] # => [4, 3] +# Omitindo o início +li[:3] # => [1, 2, 4] +# Selecione cada segunda entrada +li[::2] # => [1, 4] +# Tenha uma cópia em ordem invertida da lista +li[::-1] # => [3, 4, 2, 1] +# Use qualquer combinação dessas para indicar limites complexos +# li[inicio:fim:passo] + +# Faça uma cópia profunda de um nível usando limites +li2 = li[:] # => li2 = [1, 2, 4, 3] mas (li2 is li) resultará em False. + +# Apague elementos específicos da lista com "del" +del li[2] # li agora é [1, 2, 3] + +# Você pode somar listas +# Observação: valores em li e other_li não são modificados. +li + other_li # => [1, 2, 3, 4, 5, 6] + +# Concatene listas com "extend()" +li.extend(other_li) # Agora li é [1, 2, 3, 4, 5, 6] + +# Verifique se algo existe na lista com "in" +1 in li # => True + +# Examine tamanho com "len()" +len(li) # => 6 + + +# Tuplas são como l istas, mas imutáveis. +tup = (1, 2, 3) +tup[0] # => 1 +tup[0] = 3 # Gera um TypeError + +# Observe que uma tupla de tamanho um precisa ter uma vírgula depois do +# último elemento mas tuplas de outros tamanhos, mesmo vazias, não precisa,. +type((1)) # => <class 'int'> +type((1,)) # => <class 'tuple'> +type(()) # => <class 'tuple'> + +# Você pode realizar com tuplas a maior parte das operações que faz com listas +len(tup) # => 3 +tup + (4, 5, 6) # => (1, 2, 3, 4, 5, 6) +tup[:2] # => (1, 2) +2 in tup # => True + +# Você pode desmembrar tuplas (ou listas) em variáveis. +a, b, c = (1, 2, 3) # a é 1, b é 2 e c é 3 +# Por padrão, tuplas são criadas se você não coloca parêntesis. +d, e, f = 4, 5, 6 +# Veja como é fácil permutar dois valores +e, d = d, e # d é 5, e é 4 -# Você pode somar listas (obs: as listas originais não são modificadas) -lista + outra_lista #=> [1, 2, 3, 4, 5, 6] +# Dicionários armazenam mapeamentos +empty_dict = {} +# Aqui está um dicionário preenchido na definição da referência +filled_dict = {"um": 1, "dois": 2, "três": 3} -# Você também pode concatenar usando o método 'extend' (lista será modificada!) -lista.extend(outra_lista) # Agora lista é [1, 2, 3, 4, 5, 6] +# Observe que chaves para dicionários devem ser tipos imutáveis. Isto é para +# assegurar que a chave pode ser convertida para uma valor hash constante para +# buscas rápidas. +# Tipos imutáveis incluem inteiros, flotas, strings e tuplas. +invalid_dict = {[1,2,3]: "123"} # => Gera um TypeError: unhashable type: 'list' +valid_dict = {(1,2,3):[1,2,3]} # Já os valores, podem ser de qualquer tipo. -# Para checar se um elemento pertence a uma lista, use 'in' -1 in lista #=> True +# Acesse valores com [] +filled_dict["um"] # => 1 -# Saiba quantos elementos uma lista possui com 'len' -len(lista) #=> 6 +# Acesse todas as chaves como um iterável com "keys()". É necessário encapsular +# a chamada com um list() para transformá-las em uma lista. Falaremos sobre isso +# mais adiante. Observe que a ordem de uma chave de dicionário não é garantida. +# Por isso, os resultados aqui apresentados podem não ser exatamente como os +# aqui apresentados. +list(filled_dict.keys()) # => ["três", "dois", "um"] -# Tuplas são iguais a listas, mas são imutáveis -tup = (1, 2, 3) -tup[0] #=> 1 -tup[0] = 3 # Isso gera uma exceção do tipo TypeError - -# Você pode fazer nas tuplas todas aquelas coisas fez com a lista -len(tup) #=> 3 -tup + (4, 5, 6) #=> (1, 2, 3, 4, 5, 6) -tup[:2] #=> (1, 2) -2 in tup #=> True - -# Você pode 'desempacotar' tuplas (ou listas) em variáveis, associando cada -# elemento da tupla/lista a uma variável correspondente -a, b, c = (1, 2, 3) # a agora é 1, b agora é 2, c agora é 3 -# Tuplas são criadas por padrão, mesmo se você não usar parênteses -d, e, f = 4, 5, 6 -# Sabendo disso, veja só como é fácil trocar os valores de duas variáveis! -e, d = d, e # d agora é 5, e agora é 4 +# Acesse todos os valores de um iterável com "values()". Novamente, é +# necessário encapsular ele com list() para não termos um iterável, e sim os +# valores. Observe que, como foi dito acima, a ordem dos elementos não é +# garantida. +list(filled_dict.values()) # => [3, 2, 1] -# Dicionários armazenam 'mapeamentos' (do tipo chave-valor) -dicionario_vazio = {} -# Aqui criamos um dicionário já contendo valores -dicionario = {"um": 1, "dois": 2, "três": 3} +# Verifique a existência de chaves em um dicionário com "in" +"um" in filled_dict # => True +1 in filled_dict # => False -# Acesse valores usando [] -dicionario["um"] #=> 1 +# Acessar uma chave inexistente gera um KeyError +filled_dict["quatro"] # KeyError -# Retorna uma lista com todas as chaves do dicionário -dicionario.keys() #=> ["três", "dois", "um"] -# Nota: A ordem das chaves não é garantida. -# O resultado no seu interpretador não necessariamente será igual a esse. +# Use o método "get()" para evitar um KeyError +filled_dict.get("um") # => 1 +filled_dict.get("quatro") # => None +# O método get permite um parâmetro padrão para quando não existir a chave +filled_dict.get("um", 4) # => 1 +filled_dict.get("quatro", 4) # => 4 -# Retorna uma lista com todos os valores do dicionário -dicionario.values() #=> [3, 2, 1] -# Nota: A mesma nota acima sobre a ordenação é válida aqui. +# "setdefault()" insere em dicionário apenas se a dada chave não existir +filled_dict.setdefault("cinco", 5) # filled_dict["cinco"] tem valor 5 +filled_dict.setdefault("cinco", 6) # filled_dict["cinco"] continua 5 -# Veja se uma chave qualquer está em um dicionário usando 'in' -"um" in dicionario #=> True -1 in dicionario #=> False +# Inserindo em um dicionário +filled_dict.update({"quatro":4}) # => {"um": 1, "dois": 2, "três": 3, "quatro": 4} +#filled_dict["quatro"] = 4 #outra forma de inserir em um dicionário -# Tentar acessar uma chave que não existe gera uma exceção do tipo 'KeyError' -dicionario["quatro"] # Gera uma exceção KeyError +# Remova chaves de um dicionário com del +del filled_dict["um"] # Remove a chave "um" de filled_dict -# Você pode usar o método 'get' para evitar gerar a exceção 'KeyError'. -# Ao invés de gerar essa exceção, irá retornar 'None' se a chave não existir. -dicionario.get("um") #=> 1 -dicionario.get("quatro") #=> None -# O método 'get' suporta um argumento que diz qual valor deverá ser -# retornado se a chave não existir (ao invés de 'None'). -dicionario.get("um", 4) #=> 1 -dicionario.get("quatro", 4) #=> 4 -# O método 'setdefault' é um jeito seguro de adicionar um novo par -# chave-valor a um dicionário, associando um valor padrão imutável à uma chave -dicionario.setdefault("cinco", 5) # dicionario["cinco"] é definido como 5 -dicionario.setdefault("cinco", 6) # dicionario["cinco"] ainda é igual a 5 +# Armazenamento em sets... bem, são conjuntos +empty_set = set() +# Inicializa um set com alguns valores. Sim, ele parece um dicionário. Desculpe. +some_set = {1, 1, 2, 2, 3, 4} # some_set agora é {1, 2, 3, 4} +# Da mesma forma que chaves em um dicionário, elementos de um set devem ser +# imutáveis. +invalid_set = {[1], 1} # => Gera um TypeError: unhashable type: 'list' +valid_set = {(1,), 1} -# Conjuntos (ou sets) armazenam ... bem, conjuntos -# Nota: lembre-se que conjuntos não admitem elementos repetidos! -conjunto_vazio = set() -# Podemos inicializar um conjunto com valores -conjunto = set([1, 2, 2, 3, 4]) # conjunto é set([1, 2, 3, 4]), sem repetição! +# Pode definir novas variáveis para um conjunto +filled_set = some_set -# Desde o Python 2.7, {} pode ser usado para declarar um conjunto -conjunto = {1, 2, 2, 3, 4} # => {1 2 3 4} +# Inclua mais um item no set +filled_set.add(5) # filled_set agora é {1, 2, 3, 4, 5} -# Adicione mais ítens a um conjunto com 'add' -conjunto.add(5) # conjunto agora é {1, 2, 3, 4, 5} +# Faça interseção de conjuntos com & +other_set = {3, 4, 5, 6} +filled_set & other_set # => {3, 4, 5} -# Calcule a intersecção de dois conjuntos com & -outro_conj = {3, 4, 5, 6} -conjunto & outro_conj #=> {3, 4, 5} +# Faça união de conjuntos com | +filled_set | other_set # => {1, 2, 3, 4, 5, 6} -# Calcule a união de dois conjuntos com | -conjunto | outro_conj #=> {1, 2, 3, 4, 5, 6} +# Faça a diferença entre conjuntos com - +{1, 2, 3, 4} - {2, 3, 5} # => {1, 4} -# E a diferença entre dois conjuntos com - -{1,2,3,4} - {2,3,5} #=> {1, 4} +# Verifique a existência em um conjunto com in +2 in filled_set # => True +10 in filled_set # => False -# Veja se um elemento existe em um conjunto usando 'in' -2 in conjunto #=> True -10 in conjunto #=> False #################################################### -## 3. Controle +## 3. Controle de fluxo e iteráveis #################################################### -# Para começar, vamos apenas criar uma variável -alguma_var = 5 +# Iniciemos um variável +some_var = 5 -# Aqui está uma expressão 'if'. Veja como a identação é importante em Python! -# Esses comandos irão imprimir "alguma_var é menor que 10" -if alguma_var > 10: - print "some_var é maior que 10." -elif some_var < 10: # Esse 'elif' é opcional - print "some_var é menor que 10." -else: # Esse 'else' também é opcional - print "some_var é igual a 10." +# Aqui está uma expressão if. Indentação é significante em python! +# imprime "somevar é menor que10" +if some_var > 10: + print("some_var é absolutamente maior que 10.") +elif some_var < 10: # Esta cláusula elif é opcional. + print("some_var é menor que 10.") +else: # Isto também é opcional. + print("some_var é, de fato, 10.") """ -Laços (ou loops) 'for' iteram em listas. -Irá imprimir: +Laços for iteram sobre listas +imprime: cachorro é um mamífero gato é um mamífero rato é um mamífero """ for animal in ["cachorro", "gato", "rato"]: - # Você pode usar % para interpolar strings formatadas - print "%s é um mamífero" % animal - + # Você pode usar format() para interpolar strings formatadas + print("{} é um mamífero".format(animal)) + """ -A função `range(um número)` retorna uma lista de números -do zero até o número dado. -Irá imprimir: +"range(número)" retorna um iterável de números +de zero até o número escolhido +imprime: 0 1 2 3 """ for i in range(4): - print i + print(i) + +""" +"range(menor, maior)" gera um iterável de números +começando pelo menor até o maior +imprime: + 4 + 5 + 6 + 7 +""" +for i in range(4, 8): + print(i) """ -Laços 'while' executam enquanto uma condição dada for verdadeira. -Irá imprimir: +"range(menor, maior, passo)" retorna um iterável de números +começando pelo menor número até o maior númeno, pulando de +passo em passo. Se o passo não for indicado, o valor padrão é um. +imprime: + 4 + 6 +""" +for i in range(4, 8, 2): + print(i) +""" + +Laços while executam até que a condição não seja mais válida. +imprime: 0 1 2 @@ -319,143 +424,221 @@ Irá imprimir: """ x = 0 while x < 4: - print x - x += 1 # Isso é um atalho para a expressão x = x + 1 - -# Tratamos excessões usando o bloco try/except -# Funciona em Python 2.6 e versões superiores: + print(x) + x += 1 # Maneira mais curta para for x = x + 1 +# Lide com exceções com um bloco try/except try: - # Use 'raise' para gerar um erro - raise IndexError("Isso é um erro de índice") + # Use "raise" para gerar um erro + raise IndexError("Isto é um erro de índice") except IndexError as e: - pass # Pass é um operador que não faz nada, deixa passar. - # Usualmente você iria tratar a exceção aqui... + pass # Pass é um não-operador. Normalmente você usa algum código de recuperação aqui. +except (TypeError, NameError): + pass # Varias exceções podem ser gerenciadas, se necessário. +else: # Cláusula opcional para o bloco try/except. Deve estar após todos os blocos de exceção. + print("Tudo certo!") # Executa apenas se o código em try não gera exceção +finally: # Sempre é executado + print("Nós podemos fazer o código de limpeza aqui.") + +# Ao invés de try/finally para limpeza você pode usar a cláusula with +with open("myfile.txt") as f: + for line in f: + print(line) + +# Python provê uma abstração fundamental chamada Iterável. +# Um iterável é um objeto que pode ser tratado como uma sequência. +# O objeto retornou a função range, um iterável. + +filled_dict = {"um": 1, "dois": 2, "três": 3} +our_iterable = filled_dict.keys() +print(our_iterable) # => range(1,10). Esse é um objeto que implementa nossa interface iterável. + +# Nós podemos percorrê-la. +for i in our_iterable: + print(i) # Imprime um, dois, três + +# Mas não podemos acessar os elementos pelo seu índice. +our_iterable[1] # Gera um TypeError + +# Um iterável é um objeto que sabe como criar um iterador. +our_iterator = iter(our_iterable) + +# Nosso iterador é um objeto que pode lembrar o estado enquanto nós o percorremos. +# Nós acessamos o próximo objeto com "next()". +next(our_iterator) # => "um" + +# Ele mantém o estado enquanto nós o percorremos. +next(our_iterator) # => "dois" +next(our_iterator) # => "três" + +# Após o iterador retornar todos os seus dados, ele gera a exceção StopIterator +next(our_iterator) # Gera StopIteration + +# Você pode capturar todos os elementos de um iterador aplicando list() nele. +list(filled_dict.keys()) # => Retorna ["um", "dois", "três"] #################################################### ## 4. Funções #################################################### -# Use 'def' para definir novas funções -def soma(x, y): - print "x é %s e y é %s" % (x, y) - return x + y # Retorne valores usando 'return' +# Use "def" para criar novas funções. +def add(x, y): + print("x é {} e y é {}".format(x, y)) + return x + y # Retorne valores com a cláusula return # Chamando funções com parâmetros -soma(5, 6) #=> imprime "x é 5 e y é 6" e retorna o valor 11 +add(5, 6) # => imprime "x é 5 e y é 6" e retorna 11 -# Um outro jeito de chamar funções é especificando explicitamente os valores -# de cada parâmetro com chaves -soma(y=6, x=5) # Argumentos com chaves podem vir em qualquer ordem. +# Outro meio de chamar funções é com argumentos nomeados +add(y=6, x=5) # Argumentos nomeados podem aparecer em qualquer ordem. -# Você pode definir funções que recebem um número qualquer de argumentos -# (respeitando a sua ordem) +# Você pode definir funções que pegam um número variável de argumentos +# posicionais def varargs(*args): return args -varargs(1, 2, 3) #=> (1,2,3) +varargs(1, 2, 3) # => (1, 2, 3) +# Você pode definir funções que pegam um número variável de argumentos nomeados +# também +def keyword_args(**kwargs): + return kwargs -# Você também pode definir funções que recebem um número qualquer de argumentos -# com chaves -def args_com_chaves(**ch_args): - return ch_args +# Vamos chamá-lo para ver o que acontece +keyword_args(peh="grande", lago="ness") # => {"peh": "grande", "lago": "ness"} -# Vamos chamar essa função para ver o que acontece -args_com_chaves(pe="grande", lago="Ness") #=> {"pe": "grande", "lago": "Ness"} -# Você pode fazer as duas coisas ao mesmo tempo, se desejar -def todos_args(*args, **ch_wargs): - print args - print ch_args +# Você pode fazer ambos simultaneamente, se você quiser +def all_the_args(*args, **kwargs): + print(args) + print(kwargs) """ -todos_args(1, 2, a=3, b=4) imprime: +all_the_args(1, 2, a=3, b=4) imprime: (1, 2) {"a": 3, "b": 4} """ -# Quando você chamar funções, pode fazer o oposto do que fizemos até agora! -# Podemos usar * para expandir tuplas de argumentos e ** para expandir -# dicionários de argumentos com chave. +# Quando chamar funções, você pode fazer o oposto de args/kwargs! +# Use * para expandir tuplas e use ** para expandir dicionários! args = (1, 2, 3, 4) -ch_args = {"a": 3, "b": 4} -todos_args(*args) # equivalente a todos_args(1, 2, 3, 4) -todos_args(**ch_args) # equivalente a todos_args(a=3, b=4) -todos_args(*args, **ch_args) # equivalente a todos_args(1, 2, 3, 4, a=3, b=4) - -# Em Python, funções são elementos de primeira ordem (são como objetos, -# strings ou números) -def cria_somador(x): - def somador(y): +kwargs = {"a": 3, "b": 4} +all_the_args(*args) # equivalente a foo(1, 2, 3, 4) +all_the_args(**kwargs) # equivalente a foo(a=3, b=4) +all_the_args(*args, **kwargs) # equivalente a foo(1, 2, 3, 4, a=3, b=4) + +# Retornando múltiplos valores (com atribuição de tuplas) +def swap(x, y): + return y, x # Retorna múltiplos valores como uma tupla sem os parêntesis. + # (Observação: os parêntesis foram excluídos mas podem estar + # presentes) + +x = 1 +y = 2 +x, y = swap(x, y) # => x = 2, y = 1 +# (x, y) = swap(x,y) # Novamente, os parêntesis foram excluídos mas podem estar presentes. + +# Escopo de função +x = 5 + +def setX(num): + # A variável local x não é a mesma variável global x + x = num # => 43 + print (x) # => 43 + +def setGlobalX(num): + global x + print (x) # => 5 + x = num # variável global x agora é 6 + print (x) # => 6 + +setX(43) +setGlobalX(6) + + +# Python tem funções de primeira classe +def create_adder(x): + def adder(y): return x + y - return somador + return adder + +add_10 = create_adder(10) +add_10(3) # => 13 -soma_10 = cria_somador(10) -soma_10(3) #=> 13 +# Também existem as funções anônimas +(lambda x: x > 2)(3) # => True +(lambda x, y: x ** 2 + y ** 2)(2, 1) # => 5 -# Desta forma, existem também funções anônimas -(lambda x: x > 2)(3) #=> True +# TODO - Fix for iterables +# Existem funções internas de alta ordem +map(add_10, [1, 2, 3]) # => [11, 12, 13] +map(max, [1, 2, 3], [4, 2, 1]) # => [4, 2, 3] -# E existem funções de alta ordem por padrão -map(soma_10, [1,2,3]) #=> [11, 12, 13] -filter(lambda x: x > 5, [3, 4, 5, 6, 7]) #=> [6, 7] -reduce(lambda x, y: x + y, [3, 4, 5, 6, 7]) #=> 25 +filter(lambda x: x > 5, [3, 4, 5, 6, 7]) # => [6, 7] -# Nós podemos usar compreensão de listas para mapear e filtrar também -[soma_10(i) for i in [1, 2, 3]] #=> [11, 12, 13] -[x for x in [3, 4, 5, 6, 7] if x > 5] #=> [6, 7] +# Nós podemos usar compreensão de lista para interessantes mapas e filtros +# Compreensão de lista armazena a saída como uma lista que pode ser uma lista +# aninhada +[add_10(i) for i in [1, 2, 3]] # => [11, 12, 13] +[x for x in [3, 4, 5, 6, 7] if x > 5] # => [6, 7] #################################################### ## 5. Classes #################################################### -# Para criar uma nova classe, devemos herdar de 'object' -class Humano(object): - # Um atributo de classe. Ele é compartilhado por todas as instâncias dessa - # classe - especie = "H. sapiens" - - # Definimos um inicializador básico - def __init__(self, nome): - # Atribui o valor de argumento dado a um atributo da instância - self.nome = nome +# Nós usamos o operador "class" para ter uma classe +class Human: - # Um método de instância. Todos os métodos levam 'self' como primeiro + # Um atributo de classe. Ele é compartilhado por todas as instâncias dessa + # classe. + species = "H. sapiens" + + # Construtor básico, é chamado quando esta classe é instanciada. + # Note que dois sublinhados no início e no final de uma identificados + # significa objetos ou atributos que são usados pelo python mas vivem em + # um namespace controlado pelo usuário. Métodos (ou objetos ou atributos) + # como: __init__, __str__, __repr__, etc. são chamados métodos mágicos (ou + # algumas vezes chamados métodos dunder - "double underscore") + # Você não deve usar nomes assim por sua vontade. + def __init__(self, name): + @ Atribui o argumento ao atributo da instância + self.name = name + + # Um método de instância. Todos os métodos tem "self" como primeiro # argumento - def diga(self, msg): - return "%s: %s" % (self.nome, msg) + def say(self, msg): + return "{name}: {message}".format(name=self.name, message=msg) # Um método de classe é compartilhado por todas as instâncias - # Eles são chamados passando o nome da classe como primeiro argumento + # Eles são chamados com a classe requisitante como primeiro argumento @classmethod - def get_especie(cls): - return cls.especie + def get_species(cls): + return cls.species # Um método estático é chamado sem uma referência a classe ou instância @staticmethod - def ronca(): - return "*arrrrrrr*" + def grunt(): + return "*grunt*" # Instancie uma classe -i = Humano(nome="Ivone") -print i.diga("oi") # imprime "Ivone: oi" +i = Human(name="Ian") +print(i.say("oi")) # imprime "Ian: oi" j = Human("Joel") -print j.say("olá") #prints out "Joel: olá" +print(j.say("olá")) # imprime "Joel: olá" -# Chame nosso método de classe -i.get_especie() #=> "H. sapiens" +# Chama nosso método de classe +i.get_species() # => "H. sapiens" -# Modifique um atributo compartilhado -Humano.especie = "H. neanderthalensis" -i.get_especie() #=> "H. neanderthalensis" -j.get_especie() #=> "H. neanderthalensis" +# Altera um atributo compartilhado +Human.species = "H. neanderthalensis" +i.get_species() # => "H. neanderthalensis" +j.get_species() # => "H. neanderthalensis" -# Chame o método estático -Humano.ronca() #=> "*arrrrrrr*" +# Chama o método estático +Human.grunt() # => "*grunt*" #################################################### @@ -464,46 +647,100 @@ Humano.ronca() #=> "*arrrrrrr*" # Você pode importar módulos import math -print math.sqrt(16) #=> 4 +print(math.sqrt(16)) # => 4.0 -# Você pode importar funções específicas de um módulo +# Você pode importar apenas funções específicas de um módulo from math import ceil, floor -print ceil(3.7) #=> 4.0 -print floor(3.7) #=> 3.0 +print(ceil(3.7)) # => 4.0 +print(floor(3.7)) # => 3.0 -# Você também pode importar todas as funções de um módulo -# Atenção: isso não é recomendado! +# Você pode importar todas as funções de um módulo para o namespace atual +# Atenção: isso não é recomendado from math import * -# Você pode usar apelidos para os módulos, encurtando seus nomes +# Você pode encurtar o nome dos módulos import math as m -math.sqrt(16) == m.sqrt(16) #=> True +math.sqrt(16) == m.sqrt(16) # => True -# Módulos em Python são apenas arquivos Python. Você -# pode escrever o seu próprio módulo e importá-lo. O nome do -# módulo será o mesmo que o nome do arquivo. +# Módulos python são apenas arquivos python comuns. Você +# pode escrever os seus, e importá-los. O nome do +# módulo é o mesmo nome do arquivo. -# Você pode descobrir quais funções e atributos -# estão definidos em um módulo qualquer. +# Você pode procurar que atributos e funções definem um módulo. import math dir(math) +#################################################### +## 7. Avançado +#################################################### + +# Geradores podem ajudar você a escrever código "preguiçoso" +def double_numbers(iterable): + for i in iterable: + yield i + i + +# Um gerador cria valores conforme necessário. +# Ao invés de gerar e retornar todos os valores de uma só vez ele cria um em +# cada interação. Isto significa que valores maiores que 15 não serão +# processados em double_numbers. +# Nós usamos um sublinhado ao final do nome das variáveis quando queremos usar +# um nome que normalmente colide com uma palavra reservada do python. +range_ = range(1, 900000000) +# Multiplica por 2 todos os números até encontrar um resultado >= 30 +for i in double_numbers(range_): + print(i) + if i >= 30: + break + + +# Decoradores +# Neste exemplo beg encapsula say +# beg irá chamar say. Se say_please é verdade então ele irá mudar a mensagem +# retornada +from functools import wraps + + +def beg(target_function): + @wraps(target_function) + def wrapper(*args, **kwargs): + msg, say_please = target_function(*args, **kwargs) + if say_please: + return "{} {}".format(msg, "Por favor! Eu sou pobre :(") + return msg + + return wrapper + + +@beg +def say(say_please=False): + msg = "Você me paga uma cerveja?" + return msg, say_please + + +print(say()) # Você me paga uma cerveja? +print(say(say_please=True)) # Você me paga uma cerveja? Por favor! Eu sou pobre :( ``` ## Pronto para mais? -### Online e gratuito +### Free Online +* [Automate the Boring Stuff with Python](https://automatetheboringstuff.com) * [Learn Python The Hard Way](http://learnpythonthehardway.org/book/) * [Dive Into Python](http://www.diveintopython.net/) -* [The Official Docs](http://docs.python.org/2.6/) +* [Ideas for Python Projects](http://pythonpracticeprojects.com) +* [The Official Docs](http://docs.python.org/3/) * [Hitchhiker's Guide to Python](http://docs.python-guide.org/en/latest/) -* [Python Module of the Week](http://pymotw.com/2/) +* [A Crash Course in Python for Scientists](http://nbviewer.ipython.org/5920182) +* [Python Course](http://www.python-course.eu/index.php) +* [First Steps With Python](https://realpython.com/learn/python-first-steps/) +* [A curated list of awesome Python frameworks, libraries and software](https://github.com/vinta/awesome-python) +* [30 Python Language Features and Tricks You May Not Know About](http://sahandsaba.com/thirty-python-language-features-and-tricks-you-may-not-know.html) +* [Official Style Guide for Python](https://www.python.org/dev/peps/pep-0008/) -### Livros impressos +### Dead Tree * [Programming Python](http://www.amazon.com/gp/product/0596158106/ref=as_li_qf_sp_asin_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0596158106&linkCode=as2&tag=homebits04-20) * [Dive Into Python](http://www.amazon.com/gp/product/1441413022/ref=as_li_tf_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=1441413022&linkCode=as2&tag=homebits04-20) * [Python Essential Reference](http://www.amazon.com/gp/product/0672329786/ref=as_li_tf_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0672329786&linkCode=as2&tag=homebits04-20) - diff --git a/pt-br/python3-pt.html.markdown b/pt-br/python3-pt.html.markdown deleted file mode 100644 index 9b6bd1b6..00000000 --- a/pt-br/python3-pt.html.markdown +++ /dev/null @@ -1,746 +0,0 @@ ---- -language: python3 -contributors: - - ["Louie Dinh", "http://pythonpracticeprojects.com"] - - ["Steven Basart", "http://github.com/xksteven"] - - ["Andre Polykanine", "https://github.com/Oire"] - - ["Zachary Ferguson", "http://github.com/zfergus2"] -translators: - - ["Paulo Henrique Rodrigues Pinheiro", "http://www.sysincloud.it"] -lang: pt-br -filename: learnpython3-pt.py ---- - -Python foi criado por Guido Van Rossum nos anos 1990. Ele é atualmente uma -das mais populares linguagens em existência. Eu fiquei morrendo de amor -pelo Python por sua clareza sintática. É praticamente pseudocódigo executável. - -Suas opiniões são grandemente apreciadas. Você pode encontrar-me em -[@louiedinh](http://twitter.com/louiedinh) ou louiedinh [em] -[serviço de e-mail do google]. - -Observação: Este artigo trata de Python 3 especificamente. Verifique -[aqui](http://learnxinyminutes.com/docs/pt-br/python-pt/) se você pretende -aprender o velho Python 2.7. - -```python - -# Comentários em uma única linha começam com uma cerquilha (também conhecido por sustenido). - -""" Strings de várias linhas podem ser escritas - usando três ", e são comumente usadas - como comentários. -""" - -#################################################### -## 1. Tipos de dados primitivos e operadores -#################################################### - -# Você usa números normalmente -3 # => 3 - -# Matemática é como você espera que seja -1 + 1 # => 2 -8 - 1 # => 7 -10 * 2 # => 20 - -# Números inteiros por padrão, exceto na divisão, que retorna número -# de ponto flutuante (float). -35 / 5 # => 7.0 - -# O resultado da divisão inteira arredonda para baixo tanto para números -# positivos como para negativos. -5 // 3 # => 1 -5.0 // 3.0 # => 1.0 # funciona em float também --5 // 3 # => -2 --5.0 // 3.0 # => -2.0 - -# Quando você usa um float, o resultado é float. -3 * 2.0 # => 6.0 - -# operador módulo -7 % 3 # => 1 - -# Exponenciação (x**y, x elevado à potência y) -2**4 # => 16 - -# Determine a precedência usando parêntesis -(1 + 3) * 2 # => 8 - -# Valores lógicos são primitivos (Atenção à primeira letra maiúscula) -True -False - -# negação lógica com not -not True # => False -not False # => True - -# Operadores lógicos -# Observe que "and" e "or" são sensíveis a maiúsculas e minúsculas -True and False # => False -False or True # => True - -# Observe a utilização de operadores lógicos com números inteiros -0 and 2 # => 0 --5 or 0 # => -5 -0 == False # => True -2 == True # => False -1 == True # => True - -# Igualdade é == -1 == 1 # => True -2 == 1 # => False - -# Diferença é != -1 != 1 # => False -2 != 1 # => True - -# Mais comparações -1 < 10 # => True -1 > 10 # => False -2 <= 2 # => True -2 >= 2 # => True - -# Comparações podem ser agrupadas -1 < 2 < 3 # => True -2 < 3 < 2 # => False - -# (operador 'is' e operador '==') is verifica se duas referenciam um -# mesmo objeto, mas == verifica se as variáveis apontam para o -# mesmo valor. -a = [1, 2, 3, 4] # Referência a uma nova lista, [1, 2, 3, 4] -b = a # b referencia o que está referenciado por a -b is a # => True, a e b referenciam o mesmo objeto -b == a # => True, objetos a e b tem o mesmo conteúdo -b = [1, 2, 3, 4] # Referência a uma nova lista, [1, 2, 3, 4] -b is a # => False, a e b não referenciam o mesmo objeto -b == a # => True, objetos a e b tem o mesmo conteúdo - -# Strings são criadas com " ou ' -"Isto é uma string." -'Isto também é uma string.' - -# Strings também podem ser somadas! Mas tente não fazer isso. -"Olá " + "mundo!" # => "Olá mundo!" -# Strings podem ser somadas sem usar o '+' -"Olá " "mundo!" # => "Olá mundo!" - -# Uma string pode ser manipulada como se fosse uma lista de caracteres -"Isso é uma string"[0] # => 'I' - -# .format pode ser usado para formatar strings, dessa forma: -"{} podem ser {}".format("Strings", "interpoladas") # => "Strings podem ser interpoladas" - -# Você pode repetir os argumentos para digitar menos. -"Seja ágil {0}, seja rápido {0}, salte sobre o {1} {0}".format("Jack", "castiçal") -# => "Seja ágil Jack, seja rápido Jack, salte sobre o castiçal Jack." - -# Você pode usar palavras-chave se quiser contar. -"{nome} quer comer {comida}".format(nome="Beto", comida="lasanha") # => "Beto quer comer lasanha" - -# Se você precisa executar seu código Python3 com um interpretador Python 2.5 ou acima, você pode usar a velha forma para formatação de texto: -"%s podem ser %s da forma %s" % ("Strings", "interpoladas", "antiga") # => "Strings podem ser interpoladas da forma antiga" - - -# None é um objeto -None # => None - -# Não use o operador de igualdade "==" para comparar objetos com None -# Use "is" para isso. Ele checará pela identidade dos objetos. -"etc" is None # => False -None is None # => True - -# None, 0, e strings/listas/dicionários vazios todos retornam False. -# Qualquer outra coisa retorna True -bool(0) # => False -bool("") # => False -bool([]) # => False -bool({}) # => False - - -#################################################### -## 2. Variáveis e coleções -#################################################### - -# Python tem uma função print -print("Eu sou o Python. Prazer em conhecer!") # => Eu sou o Python. Prazer em conhecer! - -# Por padrão a função print também imprime o caractere de nova linha ao final. -# Use o argumento opcional end para mudar o caractere final. -print("Olá, Mundo", end="!") # => Olá, Mundo! - -# Forma simples para capturar dados de entrada via console -input_string_var = input("Digite alguma coisa: ") # Retorna o que foi digitado em uma string -# Observação: Em versões antigas do Python, o método input() era chamado raw_input() - -# Não é necessário declarar variáveis antes de iniciá-las -# È uma convenção usar letras_minúsculas_com_sublinhados -alguma_variavel = 5 -alguma_variavel # => 5 - -# Acessar uma variável que não tenha sido inicializada gera uma exceção. -# Veja Controle de Fluxo para aprender mais sobre tratamento de exceções. -alguma_variavel_nao_inicializada # Gera a exceção NameError - -# Listas armazenam sequencias -li = [] -# Você pode iniciar com uma lista com alguns valores -outra_li = [4, 5, 6] - -# Adicionar conteúdo ao fim da lista com append -li.append(1) # li agora é [1] -li.append(2) # li agora é [1, 2] -li.append(4) # li agora é [1, 2, 4] -li.append(3) # li agora é [1, 2, 4, 3] -# Remover do final da lista com pop -li.pop() # => 3 e agora li é [1, 2, 4] -# Vamos colocá-lo lá novamente! -li.append(3) # li agora é [1, 2, 4, 3] novamente. - -# Acessar uma lista da mesma forma que você faz com um array -li[0] # => 1 -# Acessa o último elemento -li[-1] # => 3 - -# Acessando além dos limites gera um IndexError -li[4] # Gera o IndexError - -# Você pode acessar vários elementos com a sintaxe de limites -# (É um limite fechado, aberto pra você que gosta de matemática.) -li[1:3] # => [2, 4] -# Omitindo o final -li[2:] # => [4, 3] -# Omitindo o início -li[:3] # => [1, 2, 4] -# Selecione cada segunda entrada -li[::2] # => [1, 4] -# Tenha uma cópia em ordem invertida da lista -li[::-1] # => [3, 4, 2, 1] -# Use qualquer combinação dessas para indicar limites complexos -# li[inicio:fim:passo] - -# Faça uma cópia profunda de um nível usando limites -li2 = li[:] # => li2 = [1, 2, 4, 3] mas (li2 is li) resultará em False. - -# Apague elementos específicos da lista com "del" -del li[2] # li agora é [1, 2, 3] - -# Você pode somar listas -# Observação: valores em li e other_li não são modificados. -li + other_li # => [1, 2, 3, 4, 5, 6] - -# Concatene listas com "extend()" -li.extend(other_li) # Agora li é [1, 2, 3, 4, 5, 6] - -# Verifique se algo existe na lista com "in" -1 in li # => True - -# Examine tamanho com "len()" -len(li) # => 6 - - -# Tuplas são como l istas, mas imutáveis. -tup = (1, 2, 3) -tup[0] # => 1 -tup[0] = 3 # Gera um TypeError - -# Observe que uma tupla de tamanho um precisa ter uma vírgula depois do -# último elemento mas tuplas de outros tamanhos, mesmo vazias, não precisa,. -type((1)) # => <class 'int'> -type((1,)) # => <class 'tuple'> -type(()) # => <class 'tuple'> - -# Você pode realizar com tuplas a maior parte das operações que faz com listas -len(tup) # => 3 -tup + (4, 5, 6) # => (1, 2, 3, 4, 5, 6) -tup[:2] # => (1, 2) -2 in tup # => True - -# Você pode desmembrar tuplas (ou listas) em variáveis. -a, b, c = (1, 2, 3) # a é 1, b é 2 e c é 3 -# Por padrão, tuplas são criadas se você não coloca parêntesis. -d, e, f = 4, 5, 6 -# Veja como é fácil permutar dois valores -e, d = d, e # d é 5, e é 4 - -# Dicionários armazenam mapeamentos -empty_dict = {} -# Aqui está um dicionário preenchido na definição da referência -filled_dict = {"um": 1, "dois": 2, "três": 3} - -# Observe que chaves para dicionários devem ser tipos imutáveis. Isto é para -# assegurar que a chave pode ser convertida para uma valor hash constante para -# buscas rápidas. -# Tipos imutáveis incluem inteiros, flotas, strings e tuplas. -invalid_dict = {[1,2,3]: "123"} # => Gera um TypeError: unhashable type: 'list' -valid_dict = {(1,2,3):[1,2,3]} # Já os valores, podem ser de qualquer tipo. - -# Acesse valores com [] -filled_dict["um"] # => 1 - -# Acesse todas as chaves como um iterável com "keys()". É necessário encapsular -# a chamada com um list() para transformá-las em uma lista. Falaremos sobre isso -# mais adiante. Observe que a ordem de uma chave de dicionário não é garantida. -# Por isso, os resultados aqui apresentados podem não ser exatamente como os -# aqui apresentados. -list(filled_dict.keys()) # => ["três", "dois", "um"] - - -# Acesse todos os valores de um iterável com "values()". Novamente, é -# necessário encapsular ele com list() para não termos um iterável, e sim os -# valores. Observe que, como foi dito acima, a ordem dos elementos não é -# garantida. -list(filled_dict.values()) # => [3, 2, 1] - - -# Verifique a existência de chaves em um dicionário com "in" -"um" in filled_dict # => True -1 in filled_dict # => False - -# Acessar uma chave inexistente gera um KeyError -filled_dict["quatro"] # KeyError - -# Use o método "get()" para evitar um KeyError -filled_dict.get("um") # => 1 -filled_dict.get("quatro") # => None -# O método get permite um parâmetro padrão para quando não existir a chave -filled_dict.get("um", 4) # => 1 -filled_dict.get("quatro", 4) # => 4 - -# "setdefault()" insere em dicionário apenas se a dada chave não existir -filled_dict.setdefault("cinco", 5) # filled_dict["cinco"] tem valor 5 -filled_dict.setdefault("cinco", 6) # filled_dict["cinco"] continua 5 - -# Inserindo em um dicionário -filled_dict.update({"quatro":4}) # => {"um": 1, "dois": 2, "três": 3, "quatro": 4} -#filled_dict["quatro"] = 4 #outra forma de inserir em um dicionário - -# Remova chaves de um dicionário com del -del filled_dict["um"] # Remove a chave "um" de filled_dict - - -# Armazenamento em sets... bem, são conjuntos -empty_set = set() -# Inicializa um set com alguns valores. Sim, ele parece um dicionário. Desculpe. -some_set = {1, 1, 2, 2, 3, 4} # some_set agora é {1, 2, 3, 4} - -# Da mesma forma que chaves em um dicionário, elementos de um set devem ser -# imutáveis. -invalid_set = {[1], 1} # => Gera um TypeError: unhashable type: 'list' -valid_set = {(1,), 1} - -# Pode definir novas variáveis para um conjunto -filled_set = some_set - -# Inclua mais um item no set -filled_set.add(5) # filled_set agora é {1, 2, 3, 4, 5} - -# Faça interseção de conjuntos com & -other_set = {3, 4, 5, 6} -filled_set & other_set # => {3, 4, 5} - -# Faça união de conjuntos com | -filled_set | other_set # => {1, 2, 3, 4, 5, 6} - -# Faça a diferença entre conjuntos com - -{1, 2, 3, 4} - {2, 3, 5} # => {1, 4} - -# Verifique a existência em um conjunto com in -2 in filled_set # => True -10 in filled_set # => False - - - -#################################################### -## 3. Controle de fluxo e iteráveis -#################################################### - -# Iniciemos um variável -some_var = 5 - -# Aqui está uma expressão if. Indentação é significante em python! -# imprime "somevar é menor que10" -if some_var > 10: - print("some_var é absolutamente maior que 10.") -elif some_var < 10: # Esta cláusula elif é opcional. - print("some_var é menor que 10.") -else: # Isto também é opcional. - print("some_var é, de fato, 10.") - - -""" -Laços for iteram sobre listas -imprime: - cachorro é um mamífero - gato é um mamífero - rato é um mamífero -""" -for animal in ["cachorro", "gato", "rato"]: - # Você pode usar format() para interpolar strings formatadas - print("{} é um mamífero".format(animal)) - -""" -"range(número)" retorna um iterável de números -de zero até o número escolhido -imprime: - 0 - 1 - 2 - 3 -""" -for i in range(4): - print(i) - -""" -"range(menor, maior)" gera um iterável de números -começando pelo menor até o maior -imprime: - 4 - 5 - 6 - 7 -""" -for i in range(4, 8): - print(i) - -""" -"range(menor, maior, passo)" retorna um iterável de números -começando pelo menor número até o maior númeno, pulando de -passo em passo. Se o passo não for indicado, o valor padrão é um. -imprime: - 4 - 6 -""" -for i in range(4, 8, 2): - print(i) -""" - -Laços while executam até que a condição não seja mais válida. -imprime: - 0 - 1 - 2 - 3 -""" -x = 0 -while x < 4: - print(x) - x += 1 # Maneira mais curta para for x = x + 1 - -# Lide com exceções com um bloco try/except -try: - # Use "raise" para gerar um erro - raise IndexError("Isto é um erro de índice") -except IndexError as e: - pass # Pass é um não-operador. Normalmente você usa algum código de recuperação aqui. -except (TypeError, NameError): - pass # Varias exceções podem ser gerenciadas, se necessário. -else: # Cláusula opcional para o bloco try/except. Deve estar após todos os blocos de exceção. - print("Tudo certo!") # Executa apenas se o código em try não gera exceção -finally: # Sempre é executado - print("Nós podemos fazer o código de limpeza aqui.") - -# Ao invés de try/finally para limpeza você pode usar a cláusula with -with open("myfile.txt") as f: - for line in f: - print(line) - -# Python provê uma abstração fundamental chamada Iterável. -# Um iterável é um objeto que pode ser tratado como uma sequência. -# O objeto retornou a função range, um iterável. - -filled_dict = {"um": 1, "dois": 2, "três": 3} -our_iterable = filled_dict.keys() -print(our_iterable) # => range(1,10). Esse é um objeto que implementa nossa interface iterável. - -# Nós podemos percorrê-la. -for i in our_iterable: - print(i) # Imprime um, dois, três - -# Mas não podemos acessar os elementos pelo seu índice. -our_iterable[1] # Gera um TypeError - -# Um iterável é um objeto que sabe como criar um iterador. -our_iterator = iter(our_iterable) - -# Nosso iterador é um objeto que pode lembrar o estado enquanto nós o percorremos. -# Nós acessamos o próximo objeto com "next()". -next(our_iterator) # => "um" - -# Ele mantém o estado enquanto nós o percorremos. -next(our_iterator) # => "dois" -next(our_iterator) # => "três" - -# Após o iterador retornar todos os seus dados, ele gera a exceção StopIterator -next(our_iterator) # Gera StopIteration - -# Você pode capturar todos os elementos de um iterador aplicando list() nele. -list(filled_dict.keys()) # => Retorna ["um", "dois", "três"] - - -#################################################### -## 4. Funções -#################################################### - -# Use "def" para criar novas funções. -def add(x, y): - print("x é {} e y é {}".format(x, y)) - return x + y # Retorne valores com a cláusula return - -# Chamando funções com parâmetros -add(5, 6) # => imprime "x é 5 e y é 6" e retorna 11 - -# Outro meio de chamar funções é com argumentos nomeados -add(y=6, x=5) # Argumentos nomeados podem aparecer em qualquer ordem. - -# Você pode definir funções que pegam um número variável de argumentos -# posicionais -def varargs(*args): - return args - -varargs(1, 2, 3) # => (1, 2, 3) - -# Você pode definir funções que pegam um número variável de argumentos nomeados -# também -def keyword_args(**kwargs): - return kwargs - -# Vamos chamá-lo para ver o que acontece -keyword_args(peh="grande", lago="ness") # => {"peh": "grande", "lago": "ness"} - - -# Você pode fazer ambos simultaneamente, se você quiser -def all_the_args(*args, **kwargs): - print(args) - print(kwargs) -""" -all_the_args(1, 2, a=3, b=4) imprime: - (1, 2) - {"a": 3, "b": 4} -""" - -# Quando chamar funções, você pode fazer o oposto de args/kwargs! -# Use * para expandir tuplas e use ** para expandir dicionários! -args = (1, 2, 3, 4) -kwargs = {"a": 3, "b": 4} -all_the_args(*args) # equivalente a foo(1, 2, 3, 4) -all_the_args(**kwargs) # equivalente a foo(a=3, b=4) -all_the_args(*args, **kwargs) # equivalente a foo(1, 2, 3, 4, a=3, b=4) - -# Retornando múltiplos valores (com atribuição de tuplas) -def swap(x, y): - return y, x # Retorna múltiplos valores como uma tupla sem os parêntesis. - # (Observação: os parêntesis foram excluídos mas podem estar - # presentes) - -x = 1 -y = 2 -x, y = swap(x, y) # => x = 2, y = 1 -# (x, y) = swap(x,y) # Novamente, os parêntesis foram excluídos mas podem estar presentes. - -# Escopo de função -x = 5 - -def setX(num): - # A variável local x não é a mesma variável global x - x = num # => 43 - print (x) # => 43 - -def setGlobalX(num): - global x - print (x) # => 5 - x = num # variável global x agora é 6 - print (x) # => 6 - -setX(43) -setGlobalX(6) - - -# Python tem funções de primeira classe -def create_adder(x): - def adder(y): - return x + y - return adder - -add_10 = create_adder(10) -add_10(3) # => 13 - -# Também existem as funções anônimas -(lambda x: x > 2)(3) # => True -(lambda x, y: x ** 2 + y ** 2)(2, 1) # => 5 - -# TODO - Fix for iterables -# Existem funções internas de alta ordem -map(add_10, [1, 2, 3]) # => [11, 12, 13] -map(max, [1, 2, 3], [4, 2, 1]) # => [4, 2, 3] - -filter(lambda x: x > 5, [3, 4, 5, 6, 7]) # => [6, 7] - -# Nós podemos usar compreensão de lista para interessantes mapas e filtros -# Compreensão de lista armazena a saída como uma lista que pode ser uma lista -# aninhada -[add_10(i) for i in [1, 2, 3]] # => [11, 12, 13] -[x for x in [3, 4, 5, 6, 7] if x > 5] # => [6, 7] - -#################################################### -## 5. Classes -#################################################### - - -# Nós usamos o operador "class" para ter uma classe -class Human: - - # Um atributo de classe. Ele é compartilhado por todas as instâncias dessa - # classe. - species = "H. sapiens" - - # Construtor básico, é chamado quando esta classe é instanciada. - # Note que dois sublinhados no início e no final de uma identificados - # significa objetos ou atributos que são usados pelo python mas vivem em - # um namespace controlado pelo usuário. Métodos (ou objetos ou atributos) - # como: __init__, __str__, __repr__, etc. são chamados métodos mágicos (ou - # algumas vezes chamados métodos dunder - "double underscore") - # Você não deve usar nomes assim por sua vontade. - def __init__(self, name): - @ Atribui o argumento ao atributo da instância - self.name = name - - # Um método de instância. Todos os métodos tem "self" como primeiro - # argumento - def say(self, msg): - return "{name}: {message}".format(name=self.name, message=msg) - - # Um método de classe é compartilhado por todas as instâncias - # Eles são chamados com a classe requisitante como primeiro argumento - @classmethod - def get_species(cls): - return cls.species - - # Um método estático é chamado sem uma referência a classe ou instância - @staticmethod - def grunt(): - return "*grunt*" - - -# Instancie uma classe -i = Human(name="Ian") -print(i.say("oi")) # imprime "Ian: oi" - -j = Human("Joel") -print(j.say("olá")) # imprime "Joel: olá" - -# Chama nosso método de classe -i.get_species() # => "H. sapiens" - -# Altera um atributo compartilhado -Human.species = "H. neanderthalensis" -i.get_species() # => "H. neanderthalensis" -j.get_species() # => "H. neanderthalensis" - -# Chama o método estático -Human.grunt() # => "*grunt*" - - -#################################################### -## 6. Módulos -#################################################### - -# Você pode importar módulos -import math -print(math.sqrt(16)) # => 4 - -# Você pode importar apenas funções específicas de um módulo -from math import ceil, floor -print(ceil(3.7)) # => 4.0 -print(floor(3.7)) # => 3.0 - -# Você pode importar todas as funções de um módulo para o namespace atual -# Atenção: isso não é recomendado -from math import * - -# Você pode encurtar o nome dos módulos -import math as m -math.sqrt(16) == m.sqrt(16) # => True - -# Módulos python são apenas arquivos python comuns. Você -# pode escrever os seus, e importá-los. O nome do -# módulo é o mesmo nome do arquivo. - -# Você pode procurar que atributos e funções definem um módulo. -import math -dir(math) - - -#################################################### -## 7. Avançado -#################################################### - -# Geradores podem ajudar você a escrever código "preguiçoso" -def double_numbers(iterable): - for i in iterable: - yield i + i - -# Um gerador cria valores conforme necessário. -# Ao invés de gerar e retornar todos os valores de uma só vez ele cria um em -# cada interação. Isto significa que valores maiores que 15 não serão -# processados em double_numbers. -# Nós usamos um sublinhado ao final do nome das variáveis quando queremos usar -# um nome que normalmente colide com uma palavra reservada do python. -range_ = range(1, 900000000) -# Multiplica por 2 todos os números até encontrar um resultado >= 30 -for i in double_numbers(range_): - print(i) - if i >= 30: - break - - -# Decoradores -# Neste exemplo beg encapsula say -# beg irá chamar say. Se say_please é verdade então ele irá mudar a mensagem -# retornada -from functools import wraps - - -def beg(target_function): - @wraps(target_function) - def wrapper(*args, **kwargs): - msg, say_please = target_function(*args, **kwargs) - if say_please: - return "{} {}".format(msg, "Por favor! Eu sou pobre :(") - return msg - - return wrapper - - -@beg -def say(say_please=False): - msg = "Você me paga uma cerveja?" - return msg, say_please - - -print(say()) # Você me paga uma cerveja? -print(say(say_please=True)) # Você me paga uma cerveja? Por favor! Eu sou pobre :( -``` - -## Pronto para mais? - -### Free Online - -* [Automate the Boring Stuff with Python](https://automatetheboringstuff.com) -* [Learn Python The Hard Way](http://learnpythonthehardway.org/book/) -* [Dive Into Python](http://www.diveintopython.net/) -* [Ideas for Python Projects](http://pythonpracticeprojects.com) -* [The Official Docs](http://docs.python.org/3/) -* [Hitchhiker's Guide to Python](http://docs.python-guide.org/en/latest/) -* [A Crash Course in Python for Scientists](http://nbviewer.ipython.org/5920182) -* [Python Course](http://www.python-course.eu/index.php) -* [First Steps With Python](https://realpython.com/learn/python-first-steps/) -* [A curated list of awesome Python frameworks, libraries and software](https://github.com/vinta/awesome-python) -* [30 Python Language Features and Tricks You May Not Know About](http://sahandsaba.com/thirty-python-language-features-and-tricks-you-may-not-know.html) -* [Official Style Guide for Python](https://www.python.org/dev/peps/pep-0008/) - -### Dead Tree - -* [Programming Python](http://www.amazon.com/gp/product/0596158106/ref=as_li_qf_sp_asin_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0596158106&linkCode=as2&tag=homebits04-20) -* [Dive Into Python](http://www.amazon.com/gp/product/1441413022/ref=as_li_tf_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=1441413022&linkCode=as2&tag=homebits04-20) -* [Python Essential Reference](http://www.amazon.com/gp/product/0672329786/ref=as_li_tf_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0672329786&linkCode=as2&tag=homebits04-20) diff --git a/pt-br/pythonlegacy-pt.html.markdown b/pt-br/pythonlegacy-pt.html.markdown new file mode 100644 index 00000000..572bb787 --- /dev/null +++ b/pt-br/pythonlegacy-pt.html.markdown @@ -0,0 +1,509 @@ +--- +language: Python 2 (legacy) +contributors: + - ["Louie Dinh", "http://ldinh.ca"] +translators: + - ["Vilson Vieira", "http://automata.cc"] +lang: pt-br +filename: learnpythonlegacy-pt.py +--- + +Python foi criado por Guido Van Rossum no começo dos anos 90. Atualmente é uma +das linguagens de programação mais populares. Eu me apaixonei por Python, por +sua clareza de sintaxe. É basicamente pseudocódigo executável. + +Comentários serão muito apreciados! Você pode me contactar em +[@louiedinh](http://twitter.com/louiedinh) ou louiedinh [arroba] +[serviço de email do google] + +Nota: Este artigo usa Python 2.7 especificamente, mas deveria ser aplicável a +qualquer Python 2.x. Logo haverá uma versão abordando Python 3! + +```python +# Comentários de uma linha começam com cerquilha (ou sustenido) +""" Strings de várias linhas podem ser escritas + usando três ", e são comumente usadas + como comentários +""" + +#################################################### +## 1. Tipos de dados primitivos e operadores +#################################################### + +# Você usa números normalmente +3 #=> 3 + +# Operadores matemáticos são aqueles que você já está acostumado +1 + 1 #=> 2 +8 - 1 #=> 7 +10 * 2 #=> 20 +35 / 5 #=> 7 + +# A divisão é um pouco estranha. A divisão de números inteiros arredonda +# para baixo o resultado, automaticamente +5 / 2 #=> 2 + +# Para concertar a divisão, precisamos aprender sobre números de ponto +# flutuante (conhecidos como 'float'). +2.0 # Isso é um 'float' +11.0 / 4.0 #=> 2.75 ahhh... muito melhor + +# Forçamos a precedência de operadores usando parênteses +(1 + 3) * 2 #=> 8 + +# Valores booleanos (ou 'boolean') são também tipos primitivos +True +False + +# Negamos usando 'not' +not True #=> False +not False #=> True + +# Testamos igualdade usando '==' +1 == 1 #=> True +2 == 1 #=> False + +# E desigualdade com '!=' +1 != 1 #=> False +2 != 1 #=> True + +# Mais comparações +1 < 10 #=> True +1 > 10 #=> False +2 <= 2 #=> True +2 >= 2 #=> True + +# As comparações podem ser encadeadas! +1 < 2 < 3 #=> True +2 < 3 < 2 #=> False + +# Strings são criadas com " ou ' +"Isso é uma string." +'Isso também é uma string.' + +# Strings podem ser somadas (ou melhor, concatenadas)! +"Olá " + "mundo!" #=> "Olá mundo!" + +# Uma string pode ser tratada como uma lista de caracteres +"Esta é uma string"[0] #=> 'E' + +# O caractere % pode ser usado para formatar strings, desta forma: +"%s podem ser %s" % ("strings", "interpoladas") + +# Um jeito novo de formatar strings é usando o método 'format'. +# Esse método é o jeito mais usado +"{0} podem ser {1}".format("strings", "formatadas") +# Você pode usar palavras-chave (ou 'keywords') se você não quiser contar. +"{nome} quer comer {comida}".format(nome="João", comida="lasanha") + +# 'None' é um objeto +None #=> None + +# Não use o operador de igualdade `==` para comparar objetos com 'None' +# Ao invés disso, use `is` +"etc" is None #=> False +None is None #=> True + +# O operador 'is' teste a identidade de um objeto. Isso não é +# muito útil quando estamos lidando com valores primitivos, mas é +# muito útil quando lidamos com objetos. + +# None, 0, e strings/listas vazias são todas interpretadas como 'False'. +# Todos os outros valores são 'True' +0 == False #=> True +"" == False #=> True + + +#################################################### +## 2. Variáveis e Coleções +#################################################### + +# Imprimir na tela é muito fácil +print "Eu sou o Python. Prazer em te conhecer!" + + +# Nós não precisamos declarar variáveis antes de usá-las, basta usar! +alguma_variavel = 5 # A convenção é usar caixa_baixa_com_sobrescritos +alguma_variavel #=> 5 + +# Acessar uma variável que não teve nenhum valor atribuído anteriormente é +# uma exceção. +# Veja a seção 'Controle' para aprender mais sobre tratamento de exceção. +outra_variavel # Gera uma exceção de erro de nome + +# 'if' pode ser usado como uma expressão +"uepa!" if 3 > 2 else 2 #=> "uepa!" + +# Listas armazenam sequências de elementos +lista = [] +# Você pode inicializar uma lista com valores +outra_lista = [4, 5, 6] + +# Adicione elementos no final da lista usando 'append' +lista.append(1) # lista é agora [1] +lista.append(2) # lista é agora [1, 2] +lista.append(4) # lista é agora [1, 2, 4] +lista.append(3) # lista é agora [1, 2, 4, 3] +# Remova elementos do fim da lista usando 'pop' +lista.pop() #=> 3 e lista é agora [1, 2, 4] +# Vamos adicionar o elemento novamente +lista.append(3) # lista agora é [1, 2, 4, 3] novamente. + +# Acesse elementos de uma lista através de seu índices +lista[0] #=> 1 +# Acesse o último elemento com índice negativo! +lista[-1] #=> 3 + +# Tentar acessar um elemento fora dos limites da lista gera uma exceção +# do tipo 'IndexError' +lista[4] # Gera uma exceção 'IndexError' + +# Você pode acessar vários elementos ao mesmo tempo usando a sintaxe de +# limites +# (Para quem gosta de matemática, isso é um limite fechado/aberto) +lista[1:3] #=> [2, 4] +# Você pode omitir o fim se quiser os elementos até o final da lista +lista[2:] #=> [4, 3] +# O mesmo para o início +lista[:3] #=> [1, 2, 4] + +# Remova um elemento qualquer de uma lista usando 'del' +del lista[2] # lista agora é [1, 2, 3] + +# Você pode somar listas (obs: as listas originais não são modificadas) +lista + outra_lista #=> [1, 2, 3, 4, 5, 6] + +# Você também pode concatenar usando o método 'extend' (lista será modificada!) +lista.extend(outra_lista) # Agora lista é [1, 2, 3, 4, 5, 6] + +# Para checar se um elemento pertence a uma lista, use 'in' +1 in lista #=> True + +# Saiba quantos elementos uma lista possui com 'len' +len(lista) #=> 6 + + +# Tuplas são iguais a listas, mas são imutáveis +tup = (1, 2, 3) +tup[0] #=> 1 +tup[0] = 3 # Isso gera uma exceção do tipo TypeError + +# Você pode fazer nas tuplas todas aquelas coisas fez com a lista +len(tup) #=> 3 +tup + (4, 5, 6) #=> (1, 2, 3, 4, 5, 6) +tup[:2] #=> (1, 2) +2 in tup #=> True + +# Você pode 'desempacotar' tuplas (ou listas) em variáveis, associando cada +# elemento da tupla/lista a uma variável correspondente +a, b, c = (1, 2, 3) # a agora é 1, b agora é 2, c agora é 3 +# Tuplas são criadas por padrão, mesmo se você não usar parênteses +d, e, f = 4, 5, 6 +# Sabendo disso, veja só como é fácil trocar os valores de duas variáveis! +e, d = d, e # d agora é 5, e agora é 4 + + +# Dicionários armazenam 'mapeamentos' (do tipo chave-valor) +dicionario_vazio = {} +# Aqui criamos um dicionário já contendo valores +dicionario = {"um": 1, "dois": 2, "três": 3} + +# Acesse valores usando [] +dicionario["um"] #=> 1 + +# Retorna uma lista com todas as chaves do dicionário +dicionario.keys() #=> ["três", "dois", "um"] +# Nota: A ordem das chaves não é garantida. +# O resultado no seu interpretador não necessariamente será igual a esse. + +# Retorna uma lista com todos os valores do dicionário +dicionario.values() #=> [3, 2, 1] +# Nota: A mesma nota acima sobre a ordenação é válida aqui. + +# Veja se uma chave qualquer está em um dicionário usando 'in' +"um" in dicionario #=> True +1 in dicionario #=> False + +# Tentar acessar uma chave que não existe gera uma exceção do tipo 'KeyError' +dicionario["quatro"] # Gera uma exceção KeyError + +# Você pode usar o método 'get' para evitar gerar a exceção 'KeyError'. +# Ao invés de gerar essa exceção, irá retornar 'None' se a chave não existir. +dicionario.get("um") #=> 1 +dicionario.get("quatro") #=> None +# O método 'get' suporta um argumento que diz qual valor deverá ser +# retornado se a chave não existir (ao invés de 'None'). +dicionario.get("um", 4) #=> 1 +dicionario.get("quatro", 4) #=> 4 + +# O método 'setdefault' é um jeito seguro de adicionar um novo par +# chave-valor a um dicionário, associando um valor padrão imutável à uma chave +dicionario.setdefault("cinco", 5) # dicionario["cinco"] é definido como 5 +dicionario.setdefault("cinco", 6) # dicionario["cinco"] ainda é igual a 5 + + +# Conjuntos (ou sets) armazenam ... bem, conjuntos +# Nota: lembre-se que conjuntos não admitem elementos repetidos! +conjunto_vazio = set() +# Podemos inicializar um conjunto com valores +conjunto = set([1, 2, 2, 3, 4]) # conjunto é set([1, 2, 3, 4]), sem repetição! + +# Desde o Python 2.7, {} pode ser usado para declarar um conjunto +conjunto = {1, 2, 2, 3, 4} # => {1 2 3 4} + +# Adicione mais ítens a um conjunto com 'add' +conjunto.add(5) # conjunto agora é {1, 2, 3, 4, 5} + +# Calcule a intersecção de dois conjuntos com & +outro_conj = {3, 4, 5, 6} +conjunto & outro_conj #=> {3, 4, 5} + +# Calcule a união de dois conjuntos com | +conjunto | outro_conj #=> {1, 2, 3, 4, 5, 6} + +# E a diferença entre dois conjuntos com - +{1,2,3,4} - {2,3,5} #=> {1, 4} + +# Veja se um elemento existe em um conjunto usando 'in' +2 in conjunto #=> True +10 in conjunto #=> False + + +#################################################### +## 3. Controle +#################################################### + +# Para começar, vamos apenas criar uma variável +alguma_var = 5 + +# Aqui está uma expressão 'if'. Veja como a identação é importante em Python! +# Esses comandos irão imprimir "alguma_var é menor que 10" +if alguma_var > 10: + print "some_var é maior que 10." +elif some_var < 10: # Esse 'elif' é opcional + print "some_var é menor que 10." +else: # Esse 'else' também é opcional + print "some_var é igual a 10." + + +""" +Laços (ou loops) 'for' iteram em listas. +Irá imprimir: + cachorro é um mamífero + gato é um mamífero + rato é um mamífero +""" +for animal in ["cachorro", "gato", "rato"]: + # Você pode usar % para interpolar strings formatadas + print "%s é um mamífero" % animal + +""" +A função `range(um número)` retorna uma lista de números +do zero até o número dado. +Irá imprimir: + 0 + 1 + 2 + 3 +""" +for i in range(4): + print i + +""" +Laços 'while' executam enquanto uma condição dada for verdadeira. +Irá imprimir: + 0 + 1 + 2 + 3 +""" +x = 0 +while x < 4: + print x + x += 1 # Isso é um atalho para a expressão x = x + 1 + +# Tratamos excessões usando o bloco try/except +# Funciona em Python 2.6 e versões superiores: + +try: + # Use 'raise' para gerar um erro + raise IndexError("Isso é um erro de índice") +except IndexError as e: + pass # Pass é um operador que não faz nada, deixa passar. + # Usualmente você iria tratar a exceção aqui... + + +#################################################### +## 4. Funções +#################################################### + +# Use 'def' para definir novas funções +def soma(x, y): + print "x é %s e y é %s" % (x, y) + return x + y # Retorne valores usando 'return' + +# Chamando funções com parâmetros +soma(5, 6) #=> imprime "x é 5 e y é 6" e retorna o valor 11 + +# Um outro jeito de chamar funções é especificando explicitamente os valores +# de cada parâmetro com chaves +soma(y=6, x=5) # Argumentos com chaves podem vir em qualquer ordem. + +# Você pode definir funções que recebem um número qualquer de argumentos +# (respeitando a sua ordem) +def varargs(*args): + return args + +varargs(1, 2, 3) #=> (1,2,3) + + +# Você também pode definir funções que recebem um número qualquer de argumentos +# com chaves +def args_com_chaves(**ch_args): + return ch_args + +# Vamos chamar essa função para ver o que acontece +args_com_chaves(pe="grande", lago="Ness") #=> {"pe": "grande", "lago": "Ness"} + +# Você pode fazer as duas coisas ao mesmo tempo, se desejar +def todos_args(*args, **ch_wargs): + print args + print ch_args +""" +todos_args(1, 2, a=3, b=4) imprime: + (1, 2) + {"a": 3, "b": 4} +""" + +# Quando você chamar funções, pode fazer o oposto do que fizemos até agora! +# Podemos usar * para expandir tuplas de argumentos e ** para expandir +# dicionários de argumentos com chave. +args = (1, 2, 3, 4) +ch_args = {"a": 3, "b": 4} +todos_args(*args) # equivalente a todos_args(1, 2, 3, 4) +todos_args(**ch_args) # equivalente a todos_args(a=3, b=4) +todos_args(*args, **ch_args) # equivalente a todos_args(1, 2, 3, 4, a=3, b=4) + +# Em Python, funções são elementos de primeira ordem (são como objetos, +# strings ou números) +def cria_somador(x): + def somador(y): + return x + y + return somador + +soma_10 = cria_somador(10) +soma_10(3) #=> 13 + +# Desta forma, existem também funções anônimas +(lambda x: x > 2)(3) #=> True + +# E existem funções de alta ordem por padrão +map(soma_10, [1,2,3]) #=> [11, 12, 13] +filter(lambda x: x > 5, [3, 4, 5, 6, 7]) #=> [6, 7] +reduce(lambda x, y: x + y, [3, 4, 5, 6, 7]) #=> 25 + +# Nós podemos usar compreensão de listas para mapear e filtrar também +[soma_10(i) for i in [1, 2, 3]] #=> [11, 12, 13] +[x for x in [3, 4, 5, 6, 7] if x > 5] #=> [6, 7] + +#################################################### +## 5. Classes +#################################################### + +# Para criar uma nova classe, devemos herdar de 'object' +class Humano(object): + + # Um atributo de classe. Ele é compartilhado por todas as instâncias dessa + # classe + especie = "H. sapiens" + + # Definimos um inicializador básico + def __init__(self, nome): + # Atribui o valor de argumento dado a um atributo da instância + self.nome = nome + + # Um método de instância. Todos os métodos levam 'self' como primeiro + # argumento + def diga(self, msg): + return "%s: %s" % (self.nome, msg) + + # Um método de classe é compartilhado por todas as instâncias + # Eles são chamados passando o nome da classe como primeiro argumento + @classmethod + def get_especie(cls): + return cls.especie + + # Um método estático é chamado sem uma referência a classe ou instância + @staticmethod + def ronca(): + return "*arrrrrrr*" + + +# Instancie uma classe +i = Humano(nome="Ivone") +print i.diga("oi") # imprime "Ivone: oi" + +j = Human("Joel") +print j.say("olá") #prints out "Joel: olá" + +# Chame nosso método de classe +i.get_especie() #=> "H. sapiens" + +# Modifique um atributo compartilhado +Humano.especie = "H. neanderthalensis" +i.get_especie() #=> "H. neanderthalensis" +j.get_especie() #=> "H. neanderthalensis" + +# Chame o método estático +Humano.ronca() #=> "*arrrrrrr*" + + +#################################################### +## 6. Módulos +#################################################### + +# Você pode importar módulos +import math +print math.sqrt(16) #=> 4.0 + +# Você pode importar funções específicas de um módulo +from math import ceil, floor +print ceil(3.7) #=> 4.0 +print floor(3.7) #=> 3.0 + +# Você também pode importar todas as funções de um módulo +# Atenção: isso não é recomendado! +from math import * + +# Você pode usar apelidos para os módulos, encurtando seus nomes +import math as m +math.sqrt(16) == m.sqrt(16) #=> True + +# Módulos em Python são apenas arquivos Python. Você +# pode escrever o seu próprio módulo e importá-lo. O nome do +# módulo será o mesmo que o nome do arquivo. + +# Você pode descobrir quais funções e atributos +# estão definidos em um módulo qualquer. +import math +dir(math) + + +``` + +## Pronto para mais? + +### Online e gratuito + +* [Learn Python The Hard Way](http://learnpythonthehardway.org/book/) +* [Dive Into Python](http://www.diveintopython.net/) +* [The Official Docs](http://docs.python.org/2.6/) +* [Hitchhiker's Guide to Python](http://docs.python-guide.org/en/latest/) +* [Python Module of the Week](http://pymotw.com/2/) + +### Livros impressos + +* [Programming Python](http://www.amazon.com/gp/product/0596158106/ref=as_li_qf_sp_asin_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0596158106&linkCode=as2&tag=homebits04-20) +* [Dive Into Python](http://www.amazon.com/gp/product/1441413022/ref=as_li_tf_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=1441413022&linkCode=as2&tag=homebits04-20) +* [Python Essential Reference](http://www.amazon.com/gp/product/0672329786/ref=as_li_tf_tl?ie=UTF8&camp=1789&creative=9325&creativeASIN=0672329786&linkCode=as2&tag=homebits04-20) + diff --git a/pt-br/qt-pt.html.markdown b/pt-br/qt-pt.html.markdown new file mode 100644 index 00000000..99579c35 --- /dev/null +++ b/pt-br/qt-pt.html.markdown @@ -0,0 +1,174 @@ +--- +category: tool +tool: Qt Framework +language: c++ +filename: learnqt-pt.cpp +contributors: + - ["Aleksey Kholovchuk", "https://github.com/vortexxx192"] +translators: + - ["Lucas Pugliesi", "https://github.com/fplucas"] +lang: pt-br +--- + +**Qt** é amplamente conhecido como um framework para desenvolvimento de +software multi-plataforma que pode rodar em vários outras plataformas de +softwares e hardwares com pouca ou nenhuma alteração no código, enquanto mantém +o poder e a velocidade de uma aplicação nativa. Embora o **Qt** tenha sido +originalmente escrito em *C++*, é possível utilizá-lo em outras linguagens: +*[PyQt](https://learnxinyminutes.com/docs/pyqt/)*, *QtRuby*, *PHP-Qt*, etc. + +**Qt** é ótimo para criar aplicações com interface gráfica (GUI). Esse tutorial +será feito em *C++*. + +```c++ +/* + * Vamos começar + */ + +// Todos as dependências do framework Qt iniciam com a letra 'Q' maiúscula +#include <QApplication> +#include <QLineEdit> + +int main(int argc, char *argv[]) { + // Cria um objeto para utilizar todos os recursos da aplicação + QApplication app(argc, argv); + + // Cria um widget com linha editável e exibe na tela + QLineEdit lineEdit("Hello world!"); + lineEdit.show(); + + // Inicia a aplicação em um evento de loop + return app.exec(); +} +``` + +A parte gráfica do **Qt** é toda composta de *widgets* e *conexões* entre eles. + +[LEIA MAIS SOBRE WIDGETS](http://doc.qt.io/qt-5/qtwidgets-index.html) + +```c++ +/* + * Vamos criar um label e um botão. + * Um label irá aparecer quando o botão for clicado + * + * O próprio código do Qt é autoexplicativo. + */ + +#include <QApplication> +#include <QDialog> +#include <QVBoxLayout> +#include <QPushButton> +#include <QLabel> + +int main(int argc, char *argv[]) { + QApplication app(argc, argv); + + QDialog dialogWindow; + dialogWindow.show(); + + // Adiciona um layout vertical + QVBoxLayout layout; + dialogWindow.setLayout(&layout); + + QLabel textLabel("Thanks for pressing that button"); + layout.addWidget(&textLabel); + textLabel.hide(); + + QPushButton button("Press me"); + layout.addWidget(&button); + + // Exibe o label oculto quando o botão é clicado + QObject::connect(&button, &QPushButton::pressed, + &textLabel, &QLabel::show); + + return app.exec(); +} +``` + +Veja o *QObject::connect*. O método é usado para conectar o *SINAL* de um objeto +ao *ENCAIXE* outro. + +**Sinais** são emitidos quando algo ocorre com o objeto, como quando o sinal de +*clique* é acionado apertando o QPushButton. + +**Encaixes** são *ações* que são executadas em resposta aos sinais recebidos. + +[LEIA MAIS SOBRE SINAIS E ENCAIXES](http://doc.qt.io/qt-5/signalsandslots.html) + + +A seguir vamos aprender como usar não somente o comportamento padrão dos +widgets, mas também extender seus comportamentos usando herança. Vamos criar um +botão e contar quantas vezes é pressionado. Para esse propósito definiremos +nossa própria classe *CounterLabel*. Ela deve ser declarada em um arquivo +diferente devido a estrutura específica do Qt. + +```c++ +// counterlabel.hpp + +#ifndef COUNTERLABEL +#define COUNTERLABEL + +#include <QLabel> + +class CounterLabel : public QLabel { + Q_OBJECT // Define os macros presente em todo objeto Qt + +public: + CounterLabel() : counter(0) { + setText("Counter has not been increased yet"); // método do QLabel + } + +public slots: + // Ação que será chamada em resposta ao clique do botão + void increaseCounter() { + setText(QString("Counter value: %1").arg(QString::number(++counter))); + } + +private: + int counter; +}; + +#endif // COUNTERLABEL +``` + +```c++ +// main.cpp +// Quase igual ao exemplo anterior + +#include <QApplication> +#include <QDialog> +#include <QVBoxLayout> +#include <QPushButton> +#include <QString> +#include "counterlabel.hpp" + +int main(int argc, char *argv[]) { + QApplication app(argc, argv); + + QDialog dialogWindow; + dialogWindow.show(); + + QVBoxLayout layout; + dialogWindow.setLayout(&layout); + + CounterLabel counterLabel; + layout.addWidget(&counterLabel); + + QPushButton button("Push me once more"); + layout.addWidget(&button); + QObject::connect(&button, &QPushButton::pressed, + &counterLabel, &CounterLabel::increaseCounter); + + return app.exec(); +} +``` + +É isso! Claro, o framework Qt é muito maior do que exemplificamos no tutorial, +então esteja preparado para ler e praticar mais. + +## Leitura complementar + +- [Tutoriais Qt 4.8](http://doc.qt.io/qt-4.8/tutorials.html) +- [Tutoriais Qt 5](http://doc.qt.io/qt-5/qtexamplesandtutorials.html) + +Boa sorte e divirta-se! diff --git a/pt-br/ruby-pt.html.markdown b/pt-br/ruby-pt.html.markdown index 1078f6c5..7ae28ac2 100644 --- a/pt-br/ruby-pt.html.markdown +++ b/pt-br/ruby-pt.html.markdown @@ -71,7 +71,7 @@ false.class #=> FalseClass 2 <= 2 #=> true 2 >= 2 #=> true -# Strings são objects +# Strings são objetos 'Eu sou uma string'.class #=> String "Eu também sou uma string".class #=> String diff --git a/pt-br/rust-pt.html.markdown b/pt-br/rust-pt.html.markdown new file mode 100644 index 00000000..b2bab214 --- /dev/null +++ b/pt-br/rust-pt.html.markdown @@ -0,0 +1,332 @@ +--- +language: rust +filename: rust-pt.rs +contributors: + - ["Paulo Henrique Rodrigues Pinheiro", "https://about.me/paulohrpinheiro"] +lang: pt-br + +--- + +Rust é uma linguagem de programação desenvolvida pelo Mozilla Research. Rust +combina controle de baixo nível sobre o desempenho com facilidades de alto +nível e garantias de segurança. + +Ele atinge esse objetivo sem necessitar de um coletor de lixo ou um processo +*runtime*, permitindo que se use bibliotecas Rust em substituição a bibliotecas +em C. + +A primeira versão de Rust, 0.1, apareceu em janeiro de 2012, e por três anos o +desenvolvimento correu tão rapidamente que que até recentemente o uso de +versões estáveis foi desencorajado e em vez disso a recomendação era usar as +versões empacotadas toda noite. + +Em 15 de maio de 2015, a versão 1.0 de Rust foi liberada com a garantia total +de compatibilidade reversa. Melhorias no tempo de compilação e em outros +aspectos do compilador estão disponíveis atualmente nas versões empacotadas à +noite. Rust adotou um modelo de versões *train-based* com novas versões +regularmente liberadas a cada seis semanas. A versão 1.1 beta de Rust foi +disponibilizada ao mesmo tempo que a versão 1.0. + +Apesar de Rust ser uma linguagem mais de baixo nível, Rust tem alguns conceitos +funcionais geralmente encontradas em linguagens de alto nível. Isso faz Rust +não apenas rápido, mas também fácil e eficiente para programar. + +```rust +// Isso é um comentário. Linhas de comentários são assim... +// e múltiplas linhas se parecem assim. + +/// Comentários para documentação são assim e permitem notação em markdown. +/// # Exemplos +/// +/// ``` +/// let five = 5 +/// ``` + +/////////////// +// 1. Básico // +/////////////// + +// Funções +// `i32` é o tipo para inteiros com sinal de 32 bits +fn add2(x: i32, y: i32) -> i32 { + // Implicit return (no semicolon) + x + y +} + +// Função main +fn main() { + // Números // + + // Immutable bindings + let x: i32 = 1; + + // Inteiros/Sufixos para ponto flutuante + let y: i32 = 13i32; + let f: f64 = 1.3f64; + + // Inferência de tipos + // Em geral, o compilador Rust consegue inferir qual o tipo de uma + // variável, então você não tem que escrever uma anotação explícita de tipo. + // Ao longo desse tutorial, os tipos serão explicitamente anotados em + // muitos lugares, mas apenas com propósito demonstrativo. A inferência de + // tipos pode gerenciar isso na maioria das vezes. + let implicit_x = 1; + let implicit_f = 1.3; + + // Aritmética + let sum = x + y + 13; + + // Variáveis mutáveis + let mut mutable = 1; + mutable = 4; + mutable += 2; + + // Strings // + + // String literais + let x: &str = "hello world!"; + + // Imprimindo + println!("{} {}", f, x); // 1.3 hello world + + // Uma `String` – uma String alocada no heap + let s: String = "hello world".to_string(); + + // Uma String slice - uma visão imutável em outra string. + // Basicamente, isso é um par imutável de ponteiros para uma string - ele + // não contém o conteúdo de uma strinf, apenas um ponteiro para o começo e + // um ponteiro para o fim da área de memória para a string, estaticamente + // alocada ou contida em outro objeto (nesse caso, `s`) + let s_slice: &str = &s; + + println!("{} {}", s, s_slice); // hello world hello world + + // Vetores/arrays // + + // Um array de tamanho fixo + let four_ints: [i32; 4] = [1, 2, 3, 4]; + + // Um array dinâmico (vetor) + let mut vector: Vec<i32> = vec![1, 2, 3, 4]; + vector.push(5); + + // Uma fatia – uma visão imutável em um vetor ou array + // Isso é como um string slice, mas para vetores + let slice: &[i32] = &vector; + + // Use `{:?}` para imprimir alguma coisa no estilo de depuração + println!("{:?} {:?}", vector, slice); // [1, 2, 3, 4, 5] [1, 2, 3, 4, 5] + + // Tuplas // + + // Uma tupla é um conjunto de tamanho fixo de valores de tipos + // possivelmente diferentes + let x: (i32, &str, f64) = (1, "hello", 3.4); + + // Desestruturando `let` + let (a, b, c) = x; + println!("{} {} {}", a, b, c); // 1 hello 3.4 + + // Indexando + println!("{}", x.1); // hello + + ////////////// + // 2. Tipos // + ////////////// + + // Struct + struct Point { + x: i32, + y: i32, + } + + let origin: Point = Point { x: 0, y: 0 }; + + // Uma estrutura com campos sem nome, chamada 'estrutura em tupla' + struct Point2(i32, i32); + + let origin2 = Point2(0, 0); + + // enum básico com na linguagem C + enum Direction { + Left, + Right, + Up, + Down, + } + + let up = Direction::Up; + + // Enum com campos + enum OptionalI32 { + AnI32(i32), + Nothing, + } + + let two: OptionalI32 = OptionalI32::AnI32(2); + let nothing = OptionalI32::Nothing; + + // Generics // + + struct Foo<T> { bar: T } + + // Isso é definido na biblioteca padrão como um `Option` + enum Optional<T> { + SomeVal(T), + NoVal, + } + + // Methods // + + impl<T> Foo<T> { + // Métodos recebem um parâmetro `self` explícito + fn get_bar(self) -> T { + self.bar + } + } + + let a_foo = Foo { bar: 1 }; + println!("{}", a_foo.get_bar()); // 1 + + // Traits (conhecidos como interfaces ou typeclasses em outras linguagens)// + + trait Frobnicate<T> { + fn frobnicate(self) -> Option<T>; + } + + impl<T> Frobnicate<T> for Foo<T> { + fn frobnicate(self) -> Option<T> { + Some(self.bar) + } + } + + let another_foo = Foo { bar: 1 }; + println!("{:?}", another_foo.frobnicate()); // Some(1) + + ////////////////////////////////// + // 3. Reconhecimento de padrões // + ////////////////////////////////// + + let foo = OptionalI32::AnI32(1); + match foo { + OptionalI32::AnI32(n) => println!("it’s an i32: {}", n), + OptionalI32::Nothing => println!("it’s nothing!"), + } + + // Reconhecimento avançado de padrões + struct FooBar { x: i32, y: OptionalI32 } + let bar = FooBar { x: 15, y: OptionalI32::AnI32(32) }; + + match bar { + FooBar { x: 0, y: OptionalI32::AnI32(0) } => + println!("The numbers are zero!"), + FooBar { x: n, y: OptionalI32::AnI32(m) } if n == m => + println!("The numbers are the same"), + FooBar { x: n, y: OptionalI32::AnI32(m) } => + println!("Different numbers: {} {}", n, m), + FooBar { x: _, y: OptionalI32::Nothing } => + println!("The second number is Nothing!"), + } + + ////////////////////////// + // 4. Controle de fluxo // + ////////////////////////// + + // `for` laços de repetição/iteração + let array = [1, 2, 3]; + for i in array.iter() { + println!("{}", i); + } + + // Ranges + for i in 0u32..10 { + print!("{} ", i); + } + println!(""); + // prints `0 1 2 3 4 5 6 7 8 9 ` + + // `if` + if 1 == 1 { + println!("Maths is working!"); + } else { + println!("Oh no..."); + } + + // `if` como expressão + let value = if true { + "good" + } else { + "bad" + }; + + // laço `while` de repetição + while 1 == 1 { + println!("The universe is operating normally."); + } + + // Repetição infinita + loop { + println!("Hello!"); + } + + //////////////////////////////////////// + // 5. Proteção de memória & ponteiros // + //////////////////////////////////////// + + // Ponteiro com dono - somente uma coisa pode 'possuir' esse ponteiro por + // vez. + // Isso significa que quando `Box` perde seu escopo, ele pode ser + // automaticamente desalocado com segurança. + let mut mine: Box<i32> = Box::new(3); + *mine = 5; // dereference + // Aqui, `now_its_mine` possui o controle exclusivo de `mine`. Em outras + // palavras, `mine` tem o controle transferido. + let mut now_its_mine = mine; + *now_its_mine += 2; + + println!("{}", now_its_mine); // 7 + // println!("{}", mine); // não compila porque `now_its_mine` é o dono + + // Referência - um ponteiro imutável que referencia outro dado + // Quando uma referência é dada a um valor, nós dizemos que o valor foi + // emprestado 'borrowed'. + // Quando um valor é emprestado sem ser mutável, ele não pode ser alterado + // ou ter a sua propriedade transferida. + // Um empréstimo finaliza quando o escopo em que ele foi criado termina. + + let mut var = 4; + var = 3; + let ref_var: &i32 = &var; + + println!("{}", var); // AO contrário de `mine`, `var` ainda pode ser usado + println!("{}", *ref_var); + // var = 5; // não compila porque `var` é emprestado + // *ref_var = 6; // não compila, porque `ref_var` é uma referência imutável + + // Referência mutável + // Quando um valor mutável é emprestado, ele não pode ser acessado. + let mut var2 = 4; + let ref_var2: &mut i32 = &mut var2; + *ref_var2 += 2; // '*' aponta para var2, que é mutável e emprestada + + println!("{}", *ref_var2); // 6 , // var2 não compila. + // ref_var2 é do tipo &mut i32, que guarda uma referência i32, não o valor. + // var2 = 2; // não compila porque `var2` é empretada. +} +``` + +## Outras leituras + +Existe muita coisa sobre Rust - isto aqui é apenas o básico para que você possa +entender as coisas mais importantes. Para aprender mais sobre Rust, leia [The +Rust Programming Language](http://doc.rust-lang.org/book/index.html) e +acompanhe [/r/rust](http://reddit.com/r/rust). A galera no canal #rust do +irc.mozilla.org também estão sempre dispostos a ajudar os novatos. + +Você pode brincar com outras característica de Rust com um compilador online +no portal oficial do projeto [Rust playpen](http://play.rust-lang.org), or ler +mais na página oficial [Rust website](http://rust-lang.org). + +No Brasil acompanhe os encontros do [Meetup Rust São Paulo] +(http://www.meetup.com/pt-BR/Rust-Sao-Paulo-Meetup/). + diff --git a/pt-br/sass-pt.html.markdown b/pt-br/sass-pt.html.markdown index 3d91f1ca..28df3c59 100644 --- a/pt-br/sass-pt.html.markdown +++ b/pt-br/sass-pt.html.markdown @@ -56,19 +56,19 @@ body { } -/ * Este é muito mais fácil de manter do que ter de mudar a cor -cada vez que aparece em toda a sua folha de estilo. * / +/* Este é muito mais fácil de manter do que ter de mudar a cor +cada vez que aparece em toda a sua folha de estilo. */ -/*Mixins +/* Mixins ==============================*/ -/* Se você achar que você está escrevendo o mesmo código para mais de um -elemento, você pode querer armazenar esse código em um mixin. +/* Se você achar que está escrevendo o mesmo código para mais de um +elemento, você pode armazenar esse código em um mixin. Use a diretiva '@mixin', além de um nome para o seu mixin. */ @@ -87,7 +87,7 @@ div { background-color: $primary-color; } -/* Apoś compilar ficaria assim: */ +/* Após compilar ficaria assim: */ div { display: block; margin-left: auto; @@ -128,7 +128,7 @@ div { -/*Funções +/* Funções ==============================*/ @@ -138,6 +138,7 @@ div { /* Funções pode ser chamado usando seu nome e passando o argumentos necessários */ + body { width: round(10.25px); } @@ -156,14 +157,14 @@ body { background-color: rgba(0, 0, 0, 0.75); } -/* Você também pode definir suas próprias funções. As funções são muito semelhantes aos - mixins. Ao tentar escolher entre uma função ou um mixin, lembre- - que mixins são os melhores para gerar CSS enquanto as funções são melhores para - lógica que pode ser usado em todo o seu código Sass. Os exemplos - seção Operadores Math 'são candidatos ideais para se tornar um reutilizável - função. */ +/* Você também pode definir suas próprias funções. As funções são muito semelhantes + aos mixins. Ao tentar escolher entre uma função ou um mixin, lembre + que mixins são os melhores para gerar CSS enquanto as funções são melhores para + lógica que pode ser usado em todo o seu código Sass. Os exemplos na + seção "Operações Math" são candidatos ideais para se tornar um função + reutilizável. */ -/* Esta função terá um tamanho de destino eo tamanho do pai e calcular +/* Esta função terá um tamanho de destino e o tamanho do pai (parent), calcular e voltar a percentagem */ @function calculate-percentage($target-size, $parent-size) { @@ -220,21 +221,21 @@ $main-content: calculate-percentage(600px, 960px); border-color: #22df56; } -/* Ampliando uma declaração CSS é preferível a criação de um mixin - por causa da maneira agrupa as classes que todos compartilham +/* Ao ampliar uma declaração CSS é preferível a criação de um mixin, + por causa da maneira em que agrupa as classes com todos que compartilham o mesmo estilo base. Se isso for feito com um mixin, a largura, altura, e a borda seria duplicado para cada instrução que o chamado mixin. Enquanto isso não irá afetar o seu fluxo de trabalho, será - adicionar inchaço desnecessário para os arquivos criados pelo compilador Sass. */ + adicionado inchaço desnecessário para os arquivos criados pelo compilador Sass. */ -/*Assentamento +/* Assentamento ==============================*/ -/ * Sass permite seletores ninhos dentro seletores * / +/* Sass permite seletores ninhos dentro seletores */ ul { list-style-type: none; @@ -245,7 +246,7 @@ ul { } } -/* '&' será substituído pelo selector pai. */ +/* '&' será substituído pelo selector pai (parent). */ /* Você também pode aninhar pseudo-classes. */ /* Tenha em mente que o excesso de nidificação vai fazer seu código menos sustentável. Essas práticas também recomendam não vai mais de 3 níveis de profundidade quando nidificação. @@ -290,7 +291,7 @@ ul li a { -/*Parciais e Importações +/* Parciais e Importações ==============================*/ @@ -313,7 +314,7 @@ ol { /* Sass oferece @import que pode ser usado para importar parciais em um arquivo. Isso difere da declaração CSS @import tradicional, que faz outra solicitação HTTP para buscar o arquivo importado. Sass converte os - importadas arquivo e combina com o código compilado. */ + arquivo importados e combina com o código compilado. */ @import 'reset'; @@ -322,7 +323,7 @@ body { font-family: Helvetica, Arial, Sans-serif; } -/* Compiles to: */ +/* Compila para: */ html, body, ul, ol { margin: 0; @@ -336,14 +337,14 @@ body { -/*Placeholder Selectors +/* Placeholder Selectors ==============================*/ -/* Os espaços reservados são úteis na criação de uma declaração CSS para ampliar. Se você - queria criar uma instrução CSS que foi usado exclusivamente com @extend, - Você pode fazer isso usando um espaço reservado. Espaços reservados começar com um '%' em vez - de '.' ou '#'. Espaços reservados não aparece no CSS compilado. * / +/* Os Placeholders são úteis na criação de uma declaração CSS para ampliar. Se você + deseja criar uma instrução CSS que foi usado exclusivamente com @extend, + você pode fazer isso usando um Placeholder. Placeholder começar com um '%' em vez + de '.' ou '#'. Placeholder não aparece no CSS compilado. */ %content-window { font-size: 14px; @@ -372,14 +373,14 @@ body { -/*Operações Math -============================== * / +/* Operações Math +============================== */ /* Sass fornece os seguintes operadores: +, -, *, /, e %. estes podem - ser úteis para calcular os valores diretamente no seu Sass arquivos em vez - de usar valores que você já calculados pela mão. Abaixo está um exemplo - de uma criação de um projeto simples de duas colunas. * / + ser úteis para calcular os valores diretamente no seu arquivos Sass em vez + de usar valores que você já calculados manualmente. O exemplo abaixo é + de um projeto simples de duas colunas. */ $content-area: 960px; $main-content: 600px; diff --git a/pt-br/scala-pt.html.markdown b/pt-br/scala-pt.html.markdown new file mode 100644 index 00000000..3459f567 --- /dev/null +++ b/pt-br/scala-pt.html.markdown @@ -0,0 +1,668 @@ +--- +language: Scala +filename: learnscala-pt.scala +contributors: + - ["George Petrov", "http://github.com/petrovg"] + - ["Dominic Bou-Samra", "http://dbousamra.github.com"] + - ["Geoff Liu", "http://geoffliu.me"] + - ["Ha-Duong Nguyen", "http://reference-error.org"] +translators: + - ["Francieli Viane", "https://github.com/FFrancieli"] +lang: pt-br +--- + +Scala - a linguagem escalável + +```scala + +///////////////////////////////////////////////// +// 0. O básico +///////////////////////////////////////////////// +/* + Configurando o Scala: + + 1) Baixe o instalador do Scala - http://www.scala-lang.org/downloads + 2) Extraia (unzip ou tar) para sua localização favorita e coloque o subdiretório + bin na variável de ambiente `PATH` +*/ + +/* + Tente o REPL + + Scala tem uma ferramenta chamada REPL (Read-Eval-Print Loop) que é análogo a + interpretadores de linha de comando de outras linguagens. Você pode digitar + qualquer expressão de Scala e o resultado será calculado e impresso. + + O REPL é uma ferramenta muito conveniente para testar e verificar código. Use-o + enquanto você lê o tutorial para explorar os conceitos rapidamente por conta própria. +*/ + +//Inicialize um REPL de Scala executando o comando scala no terminal. Você deve ver o prompt: +$ scala +scala> + +//Por padrão, cada expressão que você executa é salva como um novo valor enumerado: +scala> 2 + 2 +res0: Int = 4 + +// Valores padrões podem ser reutilizados. Observe o tipo do valor exibido no resultado... +scala> res0 + 2 +res1: Int = 6 + +// Scala é uma linguagem fortemente tipada. Você pode usar o REPL para verfificar o tipo +// sem avaliar uma expressão. + +scala> :type (true, 2.0) +(Boolean, Double) + +// As sessões do REPL podem ser salvas +scala> :save /sites/repl-test.scala + +//Arquivos podem ser carregados no REPL +scala> :load /sites/repl-test.scala +Loading /sites/repl-test.scala... +res2: Int = 4 +res3: Int = 6 + +// Você pode pesquisar em seu histórico recente +scala> :h? +1 2 + 2 +2 res0 + 2 +3 :save /sites/repl-test.scala +4 :load /sites/repl-test.scala +5 :h? + +// Agora que você já sabe brincar, vamos aprender um pouco de Scala... + +///////////////////////////////////////////////// +// 1. Introdução +///////////////////////////////////////////////// + +// Comentários de uma linha começam com duas barras + +/* + Comentários com múltiplas linhas, como você já pode ver, são assim. +*/ + +// Imprimir e forçar uma linha na próxima impressão +println("Hello world!") +println(10) +// Hello world! +// 10 + +//Imprimir sem forçar uma nova linha na próxima impressão +print("Hello world") +print(10) +// Hello world10 + +//A declaração de valores pode ser feita usando tanto o var quanto o val. +// Declarações feitas com `val` são imutáveis, enquanto que declarações feitas +// com var são mutáveis. Imutabilidade é uma coisa boa. +val x = 10 // x is now 10 +x = 20 // error: reassignment to val +var y = 10 + = 20 // y agora é 20 + +/* + Scala é uma linguagem estaticamente tipada. Observe ainda que nas declarações + acima nós não especificamos um tipo. Isso se deve a um recurso da linguagem + chamado de inferência. Na maioria dos casos, o compilador do Scala consegue + adivinhar qual tipo é, de forma que você não precisa digitar sempre. Nós + podemos declarar o tipo da variável de maneira explícita asim: +*/ + +val z: Int = 10 +val a: Double = 1.0 + +// Note que a conversão automática de Int para Double, o resultado é 10.0, não 10 +val b: Double = 10 + +//Valores booleanos +true +false + +//Operações booleanas +!true // false +!false // true +true == false // false +10 > 5 // true + +// Matemática é como o de costume +1 + 1 // 2 +2 - 1 // 1 +5 * 3 // 15 +6 / 2 // 3 +6 / 4 // 1 +6.0 / 4 // 1.5 +6 / 4.0 // 1.5 + +// Calcular uma expressão no REPL te dá o tipo e o valor do resultado +1 + 7 + +/* A linha acima resulta em: + scala> 1 + 7 + res29: Int = 8 + + Isso significa que o resultado ao culcular 1 + 7 é um objeto do tipo Int com + valor 8. + + Note que "res29" é o nome de uma variável gerada sequencialmente para guardar + os resultados das expressões que você executa, logo seu nome pode ser + diferente. +*/ + +"Strings em Scala são delimitadas por aspas duplas" +'a' // Um caractere em Scala +// 'Strings com aspas simples não existem em Scala.' <= isso causa um erro. + +// Strings possuem os métodos comuns de Java definidos +"hello world".length +"hello world".substring(2, 6) +"hello world".replace("C", "3") + +// Elas também possuem alguns métodos extras do Scala. Veja também: +scala.collection.immutable.StringOps +"hello world".take(5) +"hello world".drop(5) + +//Interpolação de string: observe o prefixo "s" +val n = 45 +s"We have $n apples" // => "We have 45 apples" + +// Também é possível ter expressões dentro de interpolação de strings +val a = Array(11, 9, 6) +s"My second daughter is ${a(0) - a(2)} years old." // => "My second daughter is 5 years old." +s"We have double the amount of ${n / 2.0} in apples." // => "We have double the amount of 22.5 in apples." +s"Power of 2: ${math.pow(2, 2)}" // => "Power of 2: 4" + +// Formatação de strings interpoladas com o prefixo "f" +f"Power of 5: ${math.pow(5, 2)}%1.0f" // "Power of 5: 25" +f"Square root of 122: ${math.sqrt(122)}%1.4f" // "Square root of 122: 11.0454" + + +// Strings cruas, ignorando caracteres especiais +raw"New line feed: \n. Carriage return: \r." // => "New line feed: \n. Carriage return: \r." + +//Alguns caracteres precisam ser "escapados", ex. uma aspa dupla dentro de uma string + +"They stood outside the \"Rose and Crown\"" // => "They stood outside the "Rose and Crown"" + +// Aspas triplas permitem strings a abrangerem múltiplas linhas e conter Aspas +val html = """<form id="daform"> + <p>Press belo', Joe</p> + <input type="submit"> + </form>""" + + +///////////////////////////////////////////////// +// 2. Funções +///////////////////////////////////////////////// + +// Funções são definidas da seguinte maneira: +// +// def nomeDaFuncao(args ...): TipoDeRetorno = {body ...} +// +// Se você vem de linguagens mais tradicionais, note a omissão da palavra chave +//return. Em Scala a última expressão no bloco da função é o valor de retorno +def sumOfSquares(x: Int, y: Int): Int = { + val x2 = x * x + val y2 = y * y + x2 + y2 +} + +// As { } podem ser omitidas se o corpo da função possui apenas uma expressão: +def sumOfSquaresShort(x: Int, y: Int): Int = x * x + y * y + +// A sintaxe para chamar funções é familiar: +sumOfSquares(3, 4) // => 25 + +// Você poode usar o nome dos parâmetros para especificá-los numa ordem diferente +def subtract(x: Int, y: Int): Int = x - y + +subtract(10, 3) // => 7 +subtract(y=10, x=3) // => -7 + +// Na maioria dos casos (sendo funções recursivas a a exceção mais notável) o +// tipo de retorno da função pode ser omitido, e o mesmo tipo de inferência que +// vimos nas variáveis funcionará com o valor de retorno da função: +def sq(x: Int) = x * x // O compilador consegue adivinhar que o tipo de retorno é Int + +// Funções podem ter parâmetros padrão: +def addWithDefault(x: Int, y: Int = 5) = x + y +addWithDefault(1, 2) // => 3 +addWithDefault(1) // => 6 + +// Funções anônimas são semelhantes a essa: +(x: Int) => x * x + +// Diferente de defs, até mesmo a entrada de funções anônimas podem ser omitidas +// se o contexto deixar isso claro. Observe o tipo "Int => Int", que significa +// uma função que recebe umn Int e retorna um Int. +val sq: Int => Int = x => x * x + +// Se cada argumento na sua função anônima é usado apenas uma vez, Scala te fornece +// uma maneira ainda mais curta de definí-lo. Estas funções anônimas acabam por +// ser muito comuns, como será mostrado na sessão de estrutura de dados. +val addOne: Int => Int = _ + 1 +val weirdSum: (Int, Int) => Int = (_ * 2 + _ * 3) + +addOne(5) // => 6 +weirdSum(2, 4) // => 16 + +// A palavra chave return existe em Scala, mas só retorna do def mais profundo que o cerca. +//AVISO: O uso do return em Scala é propenso a erros e deve ser evitado. +//Não há efeito em funções anônimas. Per exemplo: +def foo(x: Int): Int = { + val anonFunc: Int => Int = { z => + if (z > 5) + return z // Esta linha faz Z retornar o valor de foo! + else + z + 2 // Esta linha retorna o valor de anonFunc + } + anonFunc(x) // Esta linha retorna o valor de foo +} + +///////////////////////////////////////////////// +// 3. Controle de Fluxo +///////////////////////////////////////////////// + +1 to 5 +val r = 1 to 5 +r.foreach(println) + +r foreach println +///N.B.: Scala é bem flexível quando se fala de pontos e parêntesis - estude as regras +//separadamente. Isso ajuda a escrever DSLs e APIs que são lidas como inglês. + +(5 to 1 by -1) foreach (println) + +// Um loop while +var i = 0 +while (i < 10) { println("i " + i); i += 1 } + +while (i < 10) { println("i " + i); i += 1 } // Sim, de novo. O que aconteceu? Por quê? + +i // Exibe o valor de i. Note que o while é um loop no senso clássico - + // executa sequencialmente enquanto muda a variável do loop. While é muito + // rápido, mas usar os combinadores e compreenões acima é mais fácil + // para entender e paralizar + +// Um loop do-while +i = 0 +do { + println("i ainda é menor que 10") + i += 1 +} while (i < 10) + + +// Recursão é a forma mais idiomática de repetir uma ação em Scala (assim como na +// maioria das linguagens de programação funcional) +// Funções recursivas precisam de um tipo de retorno explícito, o compilador não +// consegue inferir; +// Aqui está o Unit +def showNumbersInRange(a: Int, b: Int): Unit = { + print(a) + if (a < b) + showNumbersInRange(a + 1, b) +} +showNumbersInRange(1, 14) + +// Condicionais + +al x = 10 + +if (x == 1) println("yeah") +if (x == 10) println("yeah") +if (x == 11) println("yeah") +if (x == 11) println("yeah") else println("nay") + +println(if (x == 10) "yeah" else "nope") +val text = if (x == 10) "yeah" else "nope" + +///////////////////////////////////////////////// +// 4. Estrutura de Dados +///////////////////////////////////////////////// + +val a = Array(1, 2, 3, 5, 8, 13) +a(0) // Int = 1 +a(3) // Int = 5 +a(21) // Lança uma exceção + +val safeM = m.withDefaultValue("no lo se") +safeM("bottle") // java.lang.String = no lo se + +val s = Set(1, 3, 7) +s(0) // Boolean = false +s(1) // Boolean = true + +/* Veja a documantação do map aqui - + * http://www.scala-lang.org/api/current/index.html#scala.collection.immutable.Map + * e garanta que você leia + */ + + // Tuplas + + (1, 2) + + (4, 3, 2) + + (1, 2, "three") + + (a, 2, "three") + + //Por que ter isso? + val divideInts = (x: Int, y: Int) => (x / y, x % y) + +//A função divideInts te dá o resultado e o resultado +divideInts(10, 3) // (Int, Int) = (3,1) + +//Para acessar os elementos de uma tupla, use _._n onde n é o índex do elemento + +val d = divideInts(10, 3) // (Int, Int) = (3,1) + +d._1 // Int = 3 +d._2 // Int = 1 + +// Alternativamente, você pode atribuir múltiplas variáveis para uma tupla, o +// que é mais conveniente e legível em muitos casos +val (div, mod) = divideInts(10, 3) + +div // Int = 3 +mod // Int = 1 + +///////////////////////////////////////////////// +// 5. Object Oriented Programming +///////////////////////////////////////////////// + +/* + Tudo o que vimos até agora neste tutorial foram expressões simples (valores, funções, etc). + Essas expressões são boas para digitar no interpretador da linha de comando para + testes rápidos, mas elas não podem existir por si só em um arquivo Scala. Por exemplo, + você não pode ter simplesmente "val x = 5" em um arquivo Scala. Ao invés disso, os únicos + construtores de alto nível permitidos em Scala são: + + - objects + - classes + - case classes + - traits + + E agora vamos explicar o que é cada um deles. +*/ + +//classes são similares a classes em outras linguagens. Os argumentos do construtor +// são declarados logo depois do nome da classe e a inicialização é feita no corpo da classe. + +class Dog(br: String) { + // codigo do construtor aqui + var breed: String = br + + // Define um método chamado bark que retorna uma String + def bark = "Woof, woof!" + + // Assume-se que os métodos e valores são públicos. As palavras chave "protected" + // e "private" também estão disponíveis. + private def sleep(hours: Int) = + println(s"I'm sleeping for $hours hours") + + // Métodos abstratos são simplesmente métodos sem corpo. Se a gente remover o + // comentário da próxima linha a classe Dog teria que ser declarada como abstrata + + // abstract class Dog(...) { ... } + // def chaseAfter(what: String): String +} + +// A palavra chave "object" cria um tipo e uma instância singlenton desse tipo. +// É comum para classes em Scala ter um "companion object" (objeto companheiro), +// onde, por exemlo, o comportamento é capturado pelas classes em si, mas o comportamento +// relacionado a toda instância da classe vai em objects. A diferença é semelhante +// a métodos versus métodos estáticos em outras linguagens. Note que objects e +// classes podem ter o mesmo nome. + +object Dog { + def allKnownBreeds = List("pitbull", "shepherd", "retriever") + def createDog(breed: String) = new Dog(breed) +} + +// Case classes são classes que possuem uma funcionalidade extra incorporada. +// Uma dúvida comum para iniciantes em Scala é quando usar classes e quando usar +// case classes. A linha é bem tênue, mas em geral classes tendem a focar em encapsulamento, +// polimorfismo e comportamento. Os valores nestas classes tendem a ser privados e +// apenas métodos ficam expostos. O propósito primário de uma case class é guardar +// dados imutáveis. Às vezes as case classes possuem alguns poucos métodos, os quais +// raramente possuem efeitos colaterais (side effects). +case class Person(name: String, phoneNumber: String) + +// Cria uma nova instância. Observe que case classes não precisam de usar "new" ao serem instanciadas +val george = Person("George", "1234") +val kate = Person("Kate", "4567") + +// Com case classes você ganha algumas regalias, como getters: +// With case classes, you get a few perks for free, like getters: +george.phoneNumber // => "1234" + +// Verificação de igualdade por campo (sem a necessidade de sobrescrever o método equals) +Person("George", "1234") == Person("Kate", "1236") // => false + +// Uma maneira fácil de copiar +// otherGeorge == Person("george", "9876") +val otherGeorge = george.copy(phoneNumber = "9876") + +// E muitas outras. Case classes também possuem pattern matching de graça. Veja no próximo tópico. + +// Traits a caminho. + + +///////////////////////////////////////////////// +// 6. Pattern Matching +///////////////////////////////////////////////// + +// Pattern matching é um recurso muito poderoso e muito usado em Scala. Aqui +// mostramos como o seu pattern se adequa a uma case class. +// NB: Diferente de outras linguagens, Scala não precisa de quebras. Entrar em +// todas as condições do pattern matching simples não acontece. + +def matchPerson(person: Person): String = person match { + // Enrão você especifica os padrões + case Person("George", number) => "We found George! His number is " + number + case Person("Kate", number) => "We found Kate! Her number is " + number + case Person(name, number) => "We matched someone : " + name + ", phone : " + number +} + +val email = "(.*)@(.*)".r // Define uma regex para o próximo exemplo. + +// Pattern matching pode parecer com o comando switch nas liguagens da família C, +// mas é muito mais poderoso. Em Scala você pode encontrar mais correpondências: + +def matchEverything(obj: Any): String = obj match { + // Você pode encontrar valores correspondentes: + case "Hello world" => "Got the string Hello world" + + // Você pode fazer correspondência por tipo: + case x: Double => "Got a Double: " + x + + // Você pode especificar condições: + case x: Int if x > 10000 => "Got a pretty big number!" + + // Você pode encontrar correspondência com case classes, como fizemos antes: + case Person(name, number) => s"Got contact info for $name!" + + // Você pode encontrar correspondências por regex: + case email(name, domain) => s"Got email address $name@$domain" + + // Você pode encontrar correspondencias por tuplas: + case (a: Int, b: Double, c: String) => s"Got a tuple: $a, $b, $c" + + // Você pode encontrar corresponências por estruturas de dados: + case List(1, b, c) => s"Got a list with three elements and starts with 1: 1, $b, $c" + + // Você pode aninhar padrões: + case List(List((1, 2, "YAY"))) => "Got a list of list of tuple" + + // Retornar qualquer valor (padrão - default) caso nenhuma das possibilidades é correspondente. + case _ => "Got unknown object" + + // Na verdade, você pode fazer correspondência de padrão de qualquer objeto que + // tenha o método "unnaply". Este recurso é tão poderoso que o Scala te deixa + // criar funções inteiras como patterns: + + val patternFunc: Person => String = { + case Person("George", number) => s"George's number: $number" + case Person(name, number) => s"Random person's number: $number" + } +} + +///////////////////////////////////////////////// +// 7. Programação Funcional +///////////////////////////////////////////////// + +// Scala permite que métodos e funções recebam ou retornem outras funções ou métodos. + +val add10: Int => Int = _ + 10 // A function taking an Int and returning an Int +List(1, 2, 3) map add10 // List(11, 12, 13) - add10 is applied to each element + +// Funções anônimas podem ser usadas ao invés de funções com nomes: +List(1, 2, 3) map (x => x + 10) + +// E o símbolo underline ("_") pode ser usado quando há apenas um argumento para a função anônima. +List(1, 2, 3) map (_ + 10) + +// Se tanto o bloco animo quanto a função que você estiver usando receberem apenas +// um argumento, você pode inclusive omitir o símbolo _ +List(1, 2, 3) map (_ + 10) + +// Combinadores + +s.map(sq) + +val sSquared = s. map(sq) + +sSquared.filter(_ < 10) + +sSquared.reduce (_+_) + +// A função filter recebe um predicado (uma função do tipo A -> Boolean) e seleciona +// todos os elementos que satisfazem o predicado. +List(1, 2, 3) filter (_ > 2) // List(3) +case class Person(name: String, age: Int) +List( + Person(name = "Dom", age = 23), + Person(name = "Bob", age = 30) +).filter(_.age > 25) // List(Person("Bob", 30)) + +// Scala tem o método foreach definido em algumas collections em específico, o qual +// recebe um tipo e retorna Unit (um método void) +val aListOfNumbers = List(1, 2, 3, 4, 10, 20, 100) +aListOfNumbers foreach (x => println(x)) +aListOfNumbers foreach println + +/* NB Ests não são laços for. A semântica dos laços for é 'repetir' enquanto um + for-comprehension define um relacionamento entre dois conjuntos de dados */ + + +///////////////////////////////////////////////// +// 8. Implicits +///////////////////////////////////////////////// + +/* ALERTA ALERTA: + Implicits são um conjunto de recursos poderosos de Scala e consequentemente é + fácil abusar deles. Iniciantes em Scala deveriam resistir a tentação de usá-los + até que eles entendam não apenas como eles funcionam mas também as melhores práticas + deles. Incluimos uma sessão neste tutorial sobre isso porque implicits são tão + corriqueiros em bibliotecas do Scala que é impossível fazer qualqeuer coisa expressiva + sem utilizar uma biblioteca que usa implicits. Isto é para você entender e trabalhar + com implicits. Não declare seus próprios implicits por conta própria. +*/ + +// qualquer valor (val, function, objects, etc) pode ser declarado para ser implícito +// usando a, você adivinhou, palavra chave "implicit". Usaremos a classe Dog definida +// na sessão 5 para os próximos exemplos. +implicit val myImplicitInt = 100 +implicit def myImplicitFunction(breed: String) = new Dog("Golden " + breed) + +// A palavra chave implicit não muda o comportamento do valor por si só, então +// os valores acima podem ser usados como de costume. +myImplicitInt + 2 // => 102 +myImplicitFunction("Pitbull").breed // => "Golden Pitbull" + +A diferença é que agora esses valores são elegíveis para serem usados quando outra +// parte do código "precisa" de um valor implícito. Uma situação é uma função +// com argumentos implícitos: +def sendGreetings(toWhom: String)(implicit howMany: Int) = + s"Hello $toWhom, $howMany blessings to you and yours!" + +// Se fornecermos um valor para "howMany" a função se comporta como sempre +sendGreetings("John")(1000) // => "Hello John, 1000 blessings to you and yours!" + +// Mas se omitirmos o parâmetro implícito um valor implícito de mesmo tipo é usado, +// neste caso, "myImplicitInt": +sendGreetings("Jane") // => "Hello Jane, 100 blessings to you and yours!" + +// Parâmetros implícitos de funções nos permitem simular type classes em outras +//linguagens funcionais. As linhas abaixo são a mesma coisa: +// def foo[T](implicit c: C[T]) = ... +// def foo[T : C] = ... + +// Outro caso no qual o compilador procura por um implicit é quando você tem obj.method(...) +// mas "obj" não possui "method" como um método. Neste caso, se houver uma conversão +// de implicit do tipo A => B, onde A é o tipo do "obj" e B tem um método chamado +// "method", a conversão é aplicada. Então, tendo myImplicitFunction acima em escopo, podemos dizer: +"Retriever".breed // => "Golden Retriever" +"Sheperd".bark // => "Woof, woof!" + +// Aqui, a String é convertida para Dog usando nossa função acima, então o método +// apropriado é chamado. Isso é um recurso extremamente poderoso, mas de novo, não +// é para ser usado de maneira leviana. Na verdade, quando você define a função +// implícita, o seu compilador deve exibir um aviso de que você não deveria fazer isso, +// a menos que você realmente saiba o que você está fazendo. + +///////////////////////////////////////////////// +// 9. Misc +///////////////////////////////////////////////// + +// Importando coisas +import scala.collection.immutable.List + +// Importando todos os sub pacotes +import scala.collection.immutable._ + +// Importando várias classes em um único comando +import scala.collection.immutable.{List, Map} + +// Renomeando um import usando '=>' +import scala.collection.immutable.{List => ImmutableList} + +// Importa todas as classes, com exceção de algumas. O import abaixo importa todas as classes excluindo Map e Set: +import scala.collection.immutable.{Map => _, Set => _, _} + +// Classes Java também podem ser importadas. A syntaxe de Scala pode ser usada: +import java.swing.{JFrame, JWindow} + +// O ponto de entrada do seu programa é definido em um arquivo Scala usando um object com um único método main: +object Application { + def main(args: Array[String]): Unit = { + // o código fica aqui + } +} + +// Arquivos podem ter múltiplas classes e objects. Compile com scalac + +// Entrada e saída + +// Para ler um arquivo linha a linha +import scala.io.Source +for(line <- Source.fromFile("myfile.txt").getLines()) + println(line) + +// Para escrever um arquivo use o PrintWriter do Javaval writer = new PrintWriter("myfile.txt") +writer.write("Writing line for line" + util.Properties.lineSeparator) +writer.write("Another line here" + util.Properties.lineSeparator) +writer.close() + +## Recursos adicionais + +* [Scala for the impatient](http://horstmann.com/scala/) +* [Twitter Scala school](http://twitter.github.io/scala_school/) +* [Documentação de Scala](http://docs.scala-lang.org/) +* [Tente Scala no seu navegador](http://scalatutorials.com/tour/) +* Junte [Scala user group](https://groups.google.com/forum/#!forum/scala-user) +``` diff --git a/pt-br/self-pt.html.markdown b/pt-br/self-pt.html.markdown index 2fb2953b..eb821474 100644 --- a/pt-br/self-pt.html.markdown +++ b/pt-br/self-pt.html.markdown @@ -147,7 +147,7 @@ o objeto '10' no slot 'x' e retornará o objeto original" # Protótipos -Não existem classes em Self. A maneira de obter um objeto é encontrar um protótipo e copia-lo. +Não existem classes em Self. A maneira de obter um objeto é encontrar um protótipo e copiá-lo. ``` | d | diff --git a/pt-br/solidity-pt.html.markdown b/pt-br/solidity-pt.html.markdown new file mode 100644 index 00000000..d4555fa7 --- /dev/null +++ b/pt-br/solidity-pt.html.markdown @@ -0,0 +1,914 @@ +--- +language: Solidity +filename: learnSolidity-br.sol +contributors: + - ["Nemil Dalal", "https://www.nemil.com"] + - ["Joseph Chow", ""] +translators: + - ["João Farias", "http://thatsabug.com/"] +lang: pt-br +--- + +Solidity permite você programar para a [Ethereum] +(https://www.ethereum.org/), uma máquina virtual baseada na tecnologia blockhain +para criação e execução de contratos inteligentes, sem necessidade de partes +centralizadas ou de confiança. + +Solidity é uma linguagem de contratos estaticamente tipaada com similaridade com +Javascript e C. Como objetos em programação orientada a objetos, cada contrato +possue variáveis de estado, funções e tipos de dados comuns. Funcionalidades +particulares de contratados incluem cláusuras modificadoras (guarda), notifica +dores de eventos para listerners e variáveis globais customizadas. + + +Exemplos de contratos Ethereum incluem crowdfunding, votações e audições cegas. + +Erros em código Solidity causam grandes riscos e custos; portanto, você +deve ser muito cuidado com teste e divulgação. DEVIDO ÀS CONSTANTES MUDANÇAS +NO ETHEREUM, ESTE DOCUMENTOS PROVAVELMENTE NÃO ESTARÁ ATUALIZADO, VOCÊ DEVE +ACOMPANHAR A CHATROOM DO SOLIDITY E O BLOG DO ETHEREUM PARA NOTÍCIAS ATUALIZADAS. +TODO CÓDIGO AQUI É ENTREGUE COMO ESTÁ, COM SUBSTANCIAL RISCO DE ERRROS E PADRÕES +DE CÓDIGO DEPRECADOS. + +Diferentemente de outros tipo de código, você também deve adicionar padrões +como pausa, deprecação e retração para reduzir riscos. Este documento discute +sintaxe, então, muito padrões populares são excluídos. + +Como Solidity e Ethereum ainda estão sob desenvolvimento, funcionalidades beta +e experimentais são tipicamente marcadas e sujeitas à mudanças. Pull requests +são bem-vindos. + +```javascript +// Primeiramente, um contrato de um Banco simples +// Permite depósitos, retiradas e checagens de saldo + +// banco_simples.sol (note a extensão .sol) + +/* **** INCICIO DO EXEMPLO **** */ + +// Declare a versão do compilador. +pragma solidity ^0.4.2; + +// Inicie com comentários Natspec (as três barras) +// usados para documentação - e como dados descritivos para elementos/ação de UI + +/// @title BancoSimples +/// @author nemild + +/* 'contrato' tem similadirades com 'classes' em outras linguagens (variáveis de +class, herança, etc.) */ + +contract BancoSimples { // CamelCase + // Declare variáveis de estado fora da função, para persistí-la durante a + // duração do contrato + + // dicionário que mapeia endereços para saldos + // tenha cuidado sobre ataques de overflow com números + + mapping (address => uint) private saldos; + + // "private" significa que outros contratos não podem acessar saldos + // diretamente, mas o dado ainda é visível para outras partes da blockchain + + address public dono; + + // ´public´ é legível (mas sem acesso de escrita) por usuários e contratos + + // Eventos - ações públicas para ouvintes externo + event LogRealizacaoDeDeposito(address numeroDaConta, uint quantidade); + + // Construtor, pode receber uma ou várias variáveis; apenas uma opção é + // permitidas + + function BancoSimples() { + // msg dá detalhes sobre a mensagem mandada pelo contrato + // msg.sender é um chamador do contrato (endereço do criador do + // contrato) + + dono = msg.sender; + } + + /// @notice Deposita ether no banco + /// @return O saldo do usuário após o depósito + + function deposito() public returns (uint) { + saldos[msg.sender] += msg.value; + + // Sem necessidade de "this." ou "self." para variáveis de estado + // todos as variáveis são inciadas com seu valor default + + LogRealizacaoDeDeposito(msg.sender, msg.value); // dispara evento + + return saldos[msg.sender]; + } + + /// @notice Retira ether do banco + /// @dev Isto não retorna nenhum ether excendente + /// @param quantidadeDeRetirada quantidade que você quer retirar + /// @return O saldo restante do usuário + function retirada(uint quantidadeDeRetirada) public returns (uint saldoRestate) { + if(saldos[msg.sender] >= quantidadeDeRetirada) { + + // Observe como deduzimos o saldo imediatamente, antes de enviar - + // devido ao risco de uma chamada recursiva que permite o chamador + // pedir um valor maior que seu saldo + + saldos[msg.sender] -= quantidadeDeRetirada; + + if (!msg.sender.send(quantidadeDeRetirada)) { + // incremente de volta só se falhar, como pode estar enviando + // para o contrato que substituiu 'enviar' no final + // do recebimento + saldos[msg.sender] += quantidadeDeRetirada; + } + } + + return saldos[msg.sender]; + } + + /// @notice Retorna o saldo + /// @return O saldo do usuário + // 'constant' evita que a função edite variáveis de estado + // permite a função executar localmente/fora da blockchain + function saldo() constant returns (uint) { + return saldos[msg.sender]; + } + + // Função de fallback - Chamada se outras funções não forem chamadas ou + // se ether sem dados forem enviados + // Tipicamente chamada quando dados inválidos são enviados + // Adicionada para que ether enviado neste contrato seja revertido se o + // contrato falhar. Se não existisse, o dinheiro do enviante é transferido + // para o contrato + function () { + throw; // 'throw' reverte o estao para antes da chamada + } +} +// ** FIM DO EXEMPLO ** + +// Agora, o básico de Solidity + + +//1 TIPO DE DADOS E MÉTODOS ASSOCIADOS +// uint é usado para quantidade de moeda (não existem doubles ou floats) +// e para datas (no sistema de tempo Unix) + +uint x; + +// int de 256 bits, não pode ser mudado após sua instanciação +int constant a = 8; +int256 constant a = 8; // mesmo efeito, mas aqui os 256 bits são explícitos +uint constant VERSÃO_ID = 0x123A1; // uma constante hexadecimal + +// com 'constant', o compilador substitui cada ocorrência com o valor + +// Para int e uint, é possível determinar o espaço explicitamente, em intervalos +// de 8 a 256, e.g., int8, int16, int24 +uint8 b; +int64 c; +uint248 e; + +// Cuidado contra overflows, e proteja-se contra esse tipo de ataque + +// Não há funções randômicas padrão, use outros contratos para este objetivo + +// Casting de tipo +int x = int(b); + +bool b = true; // ou então 'var b = true;' para inferição de tipo + +// Endereços - comportam 20 bytes/160 bits endereços Ethereum +// Não permite operações aritiméticas +address public dono; + +// Tipos de contas: +// Conta de contrato: endereço criado ao criar (função do endereço do criador, +// número da transação) +// Conta externa: (pessoa/entidade externa): endereç criado a partir de chave +// pública + +// Adicione o campo 'public' para indicar visibilidade pública/externa +// um getter é automaticamente criado, mas NÃO um setter + +// Todos os endereços podem enviar ether +dono.send(ALGUM_SALDO); // returna falso caso falhe +if (dono.send) {} // LEMBRE-SE: encapsule num 'if', dado que endereços de +// contrato tem funções executadas no envio e estas podem falhar +//Também certifique-se que os saldos deduzidos ANTES de tentar enviar, dado que +// há um risco de chamada recursiva que pode drenar um contrato + +// pode sobrescrever seu próprio + +// Pode verificar o saldo +dona.balance; // o saldo do dono (usuário ou contrato) + +// Bytes permitidos de 1 a 32 +byte a; // byte é o mesmo que bytes1 +bytes2 b; +bytes32 c; + +// Bytes dinamicamente criados + +bytes m; // Um array especial, mesmo que byte[] (mas mais comprimido) + +// Mais custoso que byte1-byte32, então, prefira estes quando possível + +// mesmo que bytes, mas não permite verificar tamanho ou acesso por indíce (por +// enquanto) + +string n = "oi"; // guardado em UTF8, note as aspas duplas, não simples + +// funções de string serão adicionadas no futuro +// prefira bytes32/bytes, dado que UTF8 usa mais espaço + +// Inferência de tipo +// var não infere tipos baseados na primeira atribuição, +// não pode ser usado em paramêtros de funções + +var a = true; + +// use com cuidado, inferência pode resultar em tipos errados +// e.g., um int8, quando um contador precisa de int16 + +// var pode ser usado para assinalar uma função a uma variável +function a(uint x) returns (uint) { + return x * 2; +} +var f = a; +f(22); // chamada + +// por padrão, todos os valores são inicializados com 0 + +// Delete pode ser chamada na maioria dos tipos +// (NÃO destroi o valor, mas retorna para o valor 0, o incial) + +uint x = 5; + +// Desestruturação/Tuplas +(x, y) = (2, 7); // assinada/troca múltiplos valores + +// 2. ESTRUTURAS DE DADOS +// Arrays + +bytes32[5] apelidos; // array estático +bytes32[] nomes; // array dinâmico +uint novoTamanho = nomes.push("João"); // adicionando retorna o novo tamanho do + +// Tamanho +nomes.length; // pega o tamanho +nomes.length = 1; // tamanhos pode ser alterados (para arrays dinâmicos) + +// arrays multidimensionais +uint x[][5]; // array com 5 arrays dinâmicos como elementos (ordem da maioria +// das linguagens) + +// Dicionários (qualquer tipo para qualquer tipo) +mapping (string => uint) public saldos; +saldos["charles"] = 1; +console.log(saldos["ada"]); // é 0, toda chave não assinalada retorna zero +// 'public' permite o seguinte contrato +nomeDoContrato.saldos("charles"); // retorna 1 +// 'public' cria um getter (mas não um setter) como o seguinte +function saldos(string _conta) returns (uint saldo) { + return saldos[_conta]; +} + +// Mapeamentos aninhados +mapping (endereco => mapping (endereco => uint)) public guardioes; + +// Para deletar +delete saldos["John"]; +delete saldos; // assinala zero para todas as chaves + +// Diferentemente de outras linguages, NÃO É POSSÍVEL iterar sobre todos os +// elementos de um mapeamento, sem saber previamente as chaves - é possível +// construir estruturas de dados personalizadas para fazer isso + +// Structs e enums +struct Banco { + address dono; + uint saldo; +} +Banco b = Banco({ + dono: msg.sender, + saldo: 5 +}); +// ou +Banco c = Banco(msg.sender, 5); + +c.quantidade = 5; // cria novo valor +delete b; +// assinala todos os valores do enum para zero, exceto mapeamentos + +// Enums +enum Estado { Criado, Travado, Inativo }; // geralmente usado para máquina de +// estados +Estado public estado; // Declara variável para enum +estado = Estado.Criado; +// enums podem ser explicitamente convertidas em ints +uint estadoCriado = uint(Estado.Criado); // 0 + +// Localização de dados: Memória vs. disco vs. pilha - todos os tipos complexos +// (arrays, structs) tem uma localização de dados +// 'memória' não é persistida, 'disco' é +// Padrão é 'disco' para variáveis locais e de estado; 'memória' para paramêtros +// de função. Pilha guarda pequena variáveis locais + +// a maioria dos tipos podem ter sua localização de dados explicitamente assinalos + +// 3. Operações simples +// Comparações, operadores binários e aritimétricos são providos +// exponenciação: ** +// ou exclusivo: ^ +// negação binária: ~ + +// 4. Variáveis Globais de nota +// ** this ** +this; // endereço do contrato +// geralmente usado no final do contrato para enviar o saldo restante às partes +this.balance; +this.algumFuncao(); // chamada de função externa via call, não via jump interno + +// ** msg - Mensagem corrente recebida pelo contrato ** ** +msg.sender; // endereço do enviador +msg.value; // quantidade de ether provida para este contrato em wei +msg.data; // bytes, todos os dados da chamada +msg.gas; // gas restante + +// ** tx - Esta transação ** +tx.origin; // endereço do enviador da transação +tx.gasprice; // valor do gas da transação + +// ** block - Informação do bloco corrente ** +now; // tempo corrente (aproxiamdo), substituto para block.timestamp +//(usa tempo do Unix) +block.number; // número do bloco corrente +block.difficulty; // dificuldade do bloco corrente +block.blockhash(1); // retorna bytes32, só funciona para os 256 blocos mais +//recentes +block.gasLimit(); + +// ** storage - Hash de disco persistente ** +storage['abc'] = 'def'; // mapea palavras de 256 bits em palavras de 256 bits + + +// 4. FUNÇÕES E MAIS +// A. Funções +// Funções simples +function incremento(uint x) returns (uint) { + x += 1; + return x; +} + +// Funções podem retornar muito argumentos, e podem especificar argumentos +// retornados sem necessidade de explicitamente usar return +function incremento(uint x, uint y) returns (uint x, uint y) { + x += 1; + y += 1; +} +// Chamando a função anterior +uint (a,b) = incremento(1,1); + +// 'constant' indica que uam função não altera variáveis persistidas +// Funções constantes são executadas localmente, não na blockchain +uint y; + +function incremento(uint x) constant returns (uint x) { + x += 1; + y += 1; // Esta linha deve falhar + // y é uma variável de estado e não pode ser alterada por uma função local +} + +// 'Especificadores de visibilidade de funções' +// Estes podem substituitir 'constante', incluíndo: +// public - visbilidade externa e interna (padrão) +// private - apenas visível no contrato corrente +// internal - apenas visível no contrato corrente e seus derivados + +// Functions hosteada - e pode ser assinalada para variável +function a() { + var z = b; + b(); +} + +function b() { + +} + +// Prefira loops sobre recursões (pilha de chamada é no máximo 1024) + +// B. Eventos +// Eventos podem notificar partes externas; facilmente buscáveis e acessáveis +// de fora da blockchain (com clientes leves) +// tipicamente declarados após os parâmetros do contrato + +// Tipicamente, com letra maiúscula - e adicione Log na frente para +// ser explicito e previnir confusão na chamada da função + +// Declaração +event LogEnvio(address indexed de, address indexed para, uint quantidade); +// Observe a letra maíscula no início do nome + +// Chamada +Envio(de, para, quantidade); + +// Para partes externas (um contrato ou entidade externo), observe: +Coin.Envio().watch({}, '', function(erro, resultado) { + if (!erro) { + console.log("Moeda transferida: " + resultado.args.quantidade + + " moedas enviadas de " + resultado.args.de + + " para " + resultado.args.para + "."); + console.log("Saldo atual:\n" + + "Enviador: " + Coin.balances.call(resultado.args.de) + + "Recebedor: " + Coin.balances.call(resultado.args.para)); + } +} +// Paradigma comum para um contrato depender de outro (e.g., um contrato que +// depende da taxa de troca provida por outro) + +// C. ModifiCadores +// MOdificadores validam entradas de funções, como saldo mínimo e autorização +// do usuário; semelhantes a guardas em outras linguagens + +// '_' (subtraço) geralmente incluído como última linha do corpo, indica que a +// função sendo chamada deve ser colocada ali +modifier apenasDepois(uint _tempo) { if (agora <= _tempo) throw; _ } +modifier apenasDono { if (msg.sender == dono) _ } +// geralmente usado para máquina de estado +modifier apenasSeEmEstado (Estado estadoCorrente) +{ if (estadoCorrente != Estado.A) _ } + +// Concatenado logo após a chamada da função +function mudeDona(novoDono) +apenasDepois(algumTempo) +apenasDono() +apenasSeEmEstado(Estado.A) +{ + dono = novoDono; +} + +// subtração pode ser incluído antes do final do corpo, mas retorno explícitos +// pode ser ignorado, então, tome cuidado +modifier chequeValor(uint quantidade) { + _ + if (msg.value > quantidade) { + uint quantidadeASerDevolvida = quantidade - msg.value; + if (!msg.sender.send(quantidadeASerDevolvida)) { + throw; + } + } +} + +// 6. BRANCHES E LOOPS + +// Todas as lógicas básicas de bloco funcionam - incluindo if/else, +// while, break, continue, return - mas não há switch + +// A sintaxe é semelhante a Javascript, mas sem conversão de tipos +// de não-booleanos para booleanos (operadores de comparação precisam +// utilizar valores booleanos) + +// Loops que dependem o comportamento do usuário exigem cuidado - dado +// que contratos tem uma quantidade máxima de gas para cada bloco de +// de código - falhas acontecerão caso ele seja excedido +// Por exemplo: +for(uint x = 0; x < listaDeEnderecoDeRefundo.length; x++) { + if (!listaDeEnderecoDeRefundo[x].send(ALGUMA_QUANTIDADE)) { + throw; + } +} + +// Dois erros acima: +// 1. Uma falha no enviar para o loop completamente, travando dinheiro +// 2. Este loop pode ser abitrariamente longo (basado na quando que +// o usuário precisa de refundo), portanto, pode falhar quando exceder +// a quantidade máxima de gas do bloco +// Ao invés disso, você deve deixar as pessoas retirarem +// individualmente de suas subcontas e marcarem a retirada + + +// 7. OBJETOS/CONTRATOS + +// A. Chamando um contrato externo +contract FonteDeInformacoes { + function info() returns (uint ret) { return 42; } +} + +contract Consumidor { + FonteDeInformacoes fonte; // aponta para um contrato na blockchain + + // Assinala variável para uma instância do contrato + function setFonte(address endereco) { + // Cast automático, cuidado; construtor não é chamado + fonte = FonteDeInformacoes(endereco); + } + + // Assinala variável para uma nova instância do contrato + function createNewFeed() { + fonte = new FonteDeInformacoes(); // nova instância criada + // construtor é chamado + } + + function chameFonte() { + // último parenteses chama o contrato, podendo adicionar + // opcionalmente valores ou gas + fonte.info.value(10).gas(800)(); + } +} + +// B. Herança + +// Ordem importa, último contrato herdado (i.e., 'def') pode +// sobrescrever partes de contratos previamente herdados +contract MeuContratdo is abc, def("um argumento personalizado def") { + +// sobrescrevendo função + function z() { + if (msg.sender == dono) { + def.z(); // chama função sobrescrita de def + super.z(); // chama função do pai imeadiato + } + } +} + +// função abstrata +function umaFuncaoAbstrata(uint x); +// não pode ser compilada, usada em contratos base/abstratos que +// então, a implementam + +// C. Import + +import "filename"; +import "github.com/ethereum/dapp-bin/library/iterable_mapping.sol"; + +// 'Import' está sobre desenvolvimento +// Atualmente não pode ser usada na linha de comando + + +// 8.OUTRAS PALAVRAS-CHAVE + +// A. Throwing +// Throwing +throw; // reverte estado e dinheiro NÃO-USADO é devolvido ao usuários +// Atualmente não pode ser capturado + +// Um padrão de design comum é: +if (!endereco.send(123)) { + throw; +} + +// B. Selfdestruct +// auto-destroe o contrato corrente, enviando fundos para o endereço +// (geralmente o criador) +selfdestruct(ALGUM_ENDERECO); + +// remove disco/código dos blocos corrente e futuros +// ajuda clientes leves, mas dados persistidos continuam no blockchain + +// Padrão comum, permite ao dono finalizar o contrato e receber fundos +// restantes +function remover() { + if(msg.sender == criador) { // Apenas o criador do contrato pode + // fazer isso + selfdestruct(criador); // Inativa o contrato e retorna os fundos + } +} + +// Talvez queria desativar o contrato manualmente, ao invés de usar +// selfdestruct (ether enviado para contratos selfdestructed é perdido) + + +// 9. NOTAS SOBRE DESIGN DE CONTRATOS + +// A. Obfuscação +// Todas as variáveis são publicamente visíveis na blockchain, então +// qualquer coisa privada precisa ser obfuscada (e.g., hash com segredo) + +// Passo-a-pass: 1. Comprometa-se com algo, 2. Revele compromisso +sha3("quantidade_de_lance", "algum segredo"); // compromisso + +// chame a função reveal (revelar) do contrato no futuros +// mostrando o lance mais o segredo para foi hasheado com SHA3 +reveal(100, "meuSegredo"); + +// B. Otimização de disco +// Escrever na blockchain pode ser caro, dado que os dados são guardados +// para sempre. É encorajado que contratos inteligentes usem memória ( +// enventualmente, compilação será melhor, mas por enquanto é benéfico +// usar estruturas de dados simples - armazenando minimamente na +// blockchain) + +// Custo pode ser alto para item como arrays multidimensionais +// (custo para guardar os dados - não declarar variáveis) + +// C. Acesso de dados da blockchain + +// Não pode restringir humanos ou computadores de ler os conteúdos +// de transações ou estado de transações + +// Enquanto 'private' previne outros *contratos* de ler dados ] +// diretamente - qualquer outra parte ainda pode ler dados da blockchain + +// Todos os dados são armazedos na blockchain, para que qualquer um +// possa observar dados antigos e mudanças + +// D. Jobs Cron +// Contratos deve ser manualmente chamados para lidar com agendamentos +// baseados em tempo; podendo criar código externo para pingar +// regularmente ou prover incentivos (ether) para outros fazê-lo + +// E. Padrão Observador +// O Padrão Observador permite que você registre um inscritor e +// registre uma função a ser chamada pelo Oráculo (nota, Oráculos pagam +// pela ação executada). Similarmente à subscrição em Pub/sub + +// Este é um contrato abstrato, tanto as classes cliente como a +// servidor importam o cliente que deve ser implementado +contract AlgumOraculoCallback { + function OraculoCallback(int _valor, uint _tempo, bytes32 info) external; +} + +contract AlgumOráculo { + AlgumOraculoCallback[] callbacks; // array com todos os inscritos + + // Registra inscrito + function addInscrito(AlgumOraculoCallback a) { + callbacks.push(a); + } + + function notificar(valor, tempo, info) private { + for(uint i = 0;i < callbacks.length; i++) { + // todos os inscritos precisam implementar AlgumOraculoCallback + callbacks[i].OraculoCallback(valor, tempo, info); + } + } + + function facaAlgo() public { + // Código para fazer algo + + // Notifica todos os inscrito + notificar(_valor, _tempo, _info); + } +} + +// Agora, seu contrato cliente pode addInscrito importando +// AlgumOraculoCallback e registrando algum Oráculo + +// F. Máquinas de estado +// veja o exemplo abaixo para o enum Estado e o modificador noEstado + +// *** EXEMPLO: Um exemplo de crowdfunding example (similar ao +// Kickstarter) *** +// ** INCIO DO EXEMPLO ** + +// FundadorDoCrowdFunding.sol + +/// @title FundadorDoCrowdFunding +/// @author nemild +contract FundadorDoCrowdFunding { + // Variáveis assinaladas na crição pelo criador + address public criador; + address public recipiente; // criador pode ser diferente do Recipiente + uint public minALevantar; // requisito para pagar, pelo contrário + // os doadores recebem o dinheiro de volta + string urlDaCampanha; + byte constant versao = 1; + + // Estruturas de dados + enum Estado { + LevantandoFundos, + RefundoExpirado, + Sucesso + } + struct Contribuicao { + uint quantidade; + address contribuidor; + } + + // Variáveis de Estado + State public estado = Estado.LevantandoFundos; // incializado na criação + uint public totalLevantado; + uint public levantadoPor; + uint public completadoEm; + Contribution[] contribuidores; + + event LogRecebimentoDeFundos(address endereco, + uint quantidade, + uint totalAtual); + event LogFundosPagos(address enderecoDoRecebedor); + + modifier noEstado(Estado _estado) { + if (estado != _estado) throw; + _ + } + + modifier eOCriador() { + if (msg.sender != criador) throw; + _ + } + + // Aguarda 6 meses após o final do contrato para destruí-lo + modifier noFimDoContrato() { + if(!((estado == Estado.RefundoExpirado || estado == Estado.Sucesso) && + completadoEm + 6 months < now)) { + throw; + } + _ + } + + function FundadorDoCrowdFunding( + uint tempoEmHorasParaFundraising, + string _urlDaCampanha, + address _recipiente, + uint _minALevantar) + { + criador = msg.sender; + recipiente = _recipiente; + urlDaCampanha = _urlDaCampanha; + minALevantar = _minALevantar; + levantadoPor = now + (tempoEmHorasParaFundraising * 1 hours); + } + + function contribuir() + public + noEstado(Estado.LevantandoFundos) + { + contribuidores.push( + Contribuicao({ + quantidade: msg.value, + contribuidor: msg.sender + }) // use array, para podermos iterar + ); + totalLevantado += msg.value; + + LogRecebimentoDeFundos(msg.sender, msg.value, totalRaised); + + verifiqueSeLevantamentoFoiCompletadoOuExpirado(); + return contribuicoes.length - 1; // retorna id + } + + function verifiqueSeLevantamentoFoiCompletadoOuExpirado() { + if (totalLevantado > minALevantar) { + estado = Estado.Sucesso; + pagar(); + + // pode incentivar enviador que iniciou a mudanção de estado + } else if ( now > levantadoPor ) { + estado = Estado.RefundoExpirado; // backers podem coletar + // o fundo chamando receberRefundo(id) + } + completadoEm = now; + } + + function pagar() + public + emEstado(Estado.Sucesso) + { + if(!recipiente.send(this.balance)) { + throw; + } + + + LogFundosPagos(fundRecipient); + } + + function receberRefundo(id) + public + emEstado(Estado.RefundoExpirado) + { + if (contribuicoes.length <= id || id < 0 || contribuicoes[id].amount == 0 ) { + throw; + } + + uint quantidadeDeRefundo = contribuicoes[id].amount; + contribuicoes[id].amount = 0; + + if(!contribuicoes[id].contribuidor.send(quantidadeParaEnviar)) { + contribuicoes[id].amount = quantidadeParaEnviar; + return false; + } + + return true; + } + + function removerContrato() + public + eOCriador() + noFimDoContrato() + { + selfdestruct(msg.sender); + // criador recebe todo o dinheiro restante{ + + } + + function () { throw; } +} +// ** FIM DO EXEMPLO ** + +// 10. OUTRAS FUNÇÕES NATIVAS + +// Unidades monetárias +// Moeda é definida usando wei, menor quantidade de ether +uint quantidadeMin = 1 wei; +uint a = 1 finney; // 1 ether == 1000 finney +// Para outras unidades, veja: http://ether.fund/tool/converter + +// Unidades temporais +1 == 1 second // segundos +1 minutes == 60 seconds // Minutos + +// Pode multiplicar uma variável de tempo, dado que unidades não são guardadas +// na variável +uint x = 5; +(x * 1 days); // 5 dias + +// Cuidado com o salto de segundos / anos com declarações de igualdade para o tempo +// (em vez disso, prefira maior que / menor que) + +// Criptografia +// Todas as string passadas são concatenadas antes de realizar hashing +sha3("ab", "cd"); +ripemd160("abc"); +sha256("def"); + +// 11. Segurança + +// Bugs são desastrosos para contratos Ethereum - até padrões Solidity populares +// podem ser considerados anti-padrões + +// Veja links para segurança no final deste documento + +// 12. FUNÇÕES DE BAIXO NÍVELS +// call - baixo nível, geralmente não usada, não tem segurança de tipos +booleanSucesso = algumEnderecoDeContrato.call('nome_da_funcao', 'arg1', 'arg2'); + +// callcode - Código no endereço alvo executado no *contexto* do contrato +// de chamada. Fornece funcionalidade de biblioteca +algumEnderecoDeContrato.callcode('nome_da_funcao'); + + +// 13. NOTAS DE ESTILO +// Baseado no guia de estilo PEP8 do Python + +// Resumo rápido: +// 4 espaços para identação +// Duas linhas separam declaração de contratos (e outras declarações de alto nível) +// Evite espaços estranhos entre parênteses +// Pode omitir chaves curly para uma declaração de linha(if, for, etc) +// else deve ser colocado na própria linha + + +// 14. COMENTÁRIOS NATSPEC +// usado para documentação, comentários e UIs externos + +// Contrato natspec - sempre acima da definição do contrato +/// @title Título do Contrato +/// @author Nome do autor + +// Função natspec +/// @notice informações sobre o que funciona; mostrado quando a função é executada +/// @dev Documentação de função para desenvolvedor + +// Parâmetro de função / valor de retorno natspec +/// @param algumParametro Alguma descrição do que o parametro faz +/// @return Descrição do valor de retorno +``` + +## Recursos adicionais +- [Documetanção Solidity](https://solidity.readthedocs.org/en/latest/) +- [Guia de Estilo do Solidity](https://ethereum.github.io/solidity//docs/style-guide/): + O guia de estilo Ethereum é derivado do guia de estilo do Python [pep8](https://www.python.org/dev/peps/pep-0008/). +- [Editor de Browser Solidity](http://chriseth.github.io/browser-solidity/) +- [Gitter Solidity Chat room](https://gitter.im/ethereum/solidity) +- [Estratégias de projeto modular para contratos Ethereum](https://docs.erisindustries.com/tutorials/solidity/) + +## Contratos de Exemplo +- [Dapp Bin](https://github.com/ethereum/dapp-bin) +- [Solidity Baby Step Contracts](https://github.com/fivedogit/solidity-baby-steps/tree/master/contracts) +- [ConsenSys Contracts](https://github.com/ConsenSys/dapp-store-contracts) +- [State of Dapps](http://dapps.ethercasts.com/) + +## Segurança +- [Thinking About Smart Contract Security](https://blog.ethereum.org/2016/06/19/thinking-smart-contract-security/) +- [Smart Contract Security](https://blog.ethereum.org/2016/06/10/smart-contract-security/) +- [Hacking Distributed Blog](http://hackingdistributed.com/) + +## Informação excluída intencionalmente +- Libraries + +## Estilo +- [PEP8](https://www.python.org/dev/peps/pep-0008/) é usado como guia de estilo, + incluindo sua filosofia geral + +## Editores +- [Vim Solidity](https://github.com/tomlion/vim-solidity) +- Snippets de Editores ([Ultisnips format](https://gist.github.com/nemild/98343ce6b16b747788bc)) + +## Trabalhos Futuros +- Novas palavras-chave: protected, inheritable +- Lista de padrões de design comuns (throttling, RNG, atualização de versão) +- Padrões anti-segurança comuns + + +Sinta-se a vontade para enviar um pull request com quaisquer edições - ou email +para nemild - / at- / gmail diff --git a/pt-br/stylus-pt.html.markdown b/pt-br/stylus-pt.html.markdown new file mode 100755 index 00000000..40c3c02c --- /dev/null +++ b/pt-br/stylus-pt.html.markdown @@ -0,0 +1,228 @@ +--- +language: stylus +filename: learnStylus-pt.styl +contributors: + - ["Salomão Neto", "https://github.com/salomaosnff"] + - ["Isaac Henrique", "https://github.com/Isaachi1"] +lang: pt-br +--- + +Stylus tem como propósito, adicionar funcionalidades às suas folhas de estilos CSS que te ajudam no desenvolvimento, sem que haja a quebra de compartibilidade entre os navegadores Web. +Entre elas estão variáveis, aninhamento, mixins, funções e muito mais. + +A sintaxe do Stylus é muito flexivel podendo utilizar a sintaxe padrão do CSS e deixando opcional o ponto e vírgula (;), dois pontos (:) e até mesmo as chaves ({ e }), tornando assim o seu código ainda mais legível. + +Stylus não fornece novas opções de estilos, mas dá funcionalidades que permitem deixar seu CSS muito mais dinâmico. + + +```scss + +/* Estilo de código +==============================*/ + +/* As chaves, ponto e vírgula, e dois pontos são opcionais no Stylus. */ + +body { + background: #000; +} + +body { + background: #000 +} + +body { + background #000 +} + +body + background #000 + +body + background: #000; + +body + background: #000 + + +// Comentários de linha única são removidos quando Stylus é compilado para CSS. + +/* Comentários multi-line são preservados. */ + + +/* Seletores +==============================*/ + +/* Selecionando elementos dentro de outro elemento */ +body { + background: #000000; + h1 { + color: #FF0000; + } +} + +/* Ou se preferir... */ +body + background #000000 + h1 + color #FF0000 + + +/* Obtendo a referência do elemento pai +==============================*/ +a { + color: #0088dd; + &:hover { + color: #DD8800; + } +} + + +/*Variáveis +==============================*/ + + +/* + É possível armazenar um valor CSS (tais como a cor) de uma variável. + Embora seja opcional, é recomendado adicionar $ antes de um nome de variável + para que você possa distinguir uma variável de outro valor CSS. +*/ + +$primary-color = #A3A4FF +$secondary-color = #51527F +$body-font = 'Roboto', sans-serif + +/* Você pode usar as variáveis em toda a sua folha de estilo. +Agora, se você quer mudar a cor, você só tem que fazer a mudança uma vez. */ + +body + background-color $primary-color + color $secondary-color + font-family $body-font + +/* Quando compilar ficaria assim: */ +body { + background-color: #A3A4FF; + color: #51527F; + font-family: 'Roboto', sans-serif; +} + +/ * +Este é muito mais fácil de manter do que ter de mudar a cor +cada vez que aparece em toda a sua folha de estilo. +* / + + + +/*Mixins +==============================*/ + +/* Se você achar que você está escrevendo o mesmo código para mais de um +elemento, você pode querer armazenar esse código em um mixin. + +center() + display block + margin-left auto + margin-right auto + left 0 + right 0 + +/* Utilizando um mixin */ +body { + center() + background-color: $primary-color +} + +/* Após compilar ficaria assim: */ +div { + display: block; + margin-left: auto; + margin-right: auto; + left: 0; + right: 0; + background-color: #A3A4FF; +} + +/* Você pode usar mixins para criar uma propriedade estenográfica. */ + +size($width, $height) + width $width + height $height + +.rectangle + size(100px, 60px) + +.square + size(40px, 40px) + +/* Você pode usar um mixin como uma propriedade CSS. */ +circle($ratio) + width $ratio * 2 + height $ratio * 2 + border-radius $ratio + +.ball + circle 25px + + +/* Interpolação +==============================*/ + +vendor(prop, args) + -webkit-{prop} args + -moz-{prop} args + {prop} args + +border-radius() + vendor('border-radius', arguments) + +box-shadow() + vendor('box-shadow', arguments) + +button + border-radius 1px 2px / 3px 4px + +/* Funções +==============================*/ + +/* Funções no Stylus permitem fazer uma variedade de tarefas, como por exemplo, manipular algum dado. */ + +body { + background darken(#0088DD, 50%) // Escurece a cor #0088DD em 50% +} + +/* Criando sua própria função */ +somar(a, b) + a + b + +body + padding somar(10px, 5) + +/* Condições +==============================*/ +comparar(a, b) + if a > b + maior + else if a < b + menor + else + igual + +comparar(5, 2) // => maior +comparar(1, 5) // => menor +comparar(10, 10) // => igual + +/* Iterações +==============================*/ + +/** +Sintaxe de laço de repetição for: +for <val-name> [, <key-name>] in <expression> +**/ + +for $item in (1..2) /* Repete o bloco 12 vezes */ + .col-{$item} + width ($item / 12) * 100% /* Calcula a largura pelo número da coluna* + +``` + +Agora que você conhece um pouco sobre esse poderoso pré-processador de CSS, você está pronto para criar folhas de estilos mais dinâmicas. Para aprofundar seus conhecimentos visite a documentação oficial do stylus em http://stylus-lang.com. diff --git a/pt-br/swift-pt.html.markdown b/pt-br/swift-pt.html.markdown index 4ad67a06..bf410352 100644 --- a/pt-br/swift-pt.html.markdown +++ b/pt-br/swift-pt.html.markdown @@ -1,12 +1,13 @@ --- language: swift +filename: learnswift-pt.swift contributors: - ["Grant Timmerman", "http://github.com/grant"] - ["Christopher Bess", "http://github.com/cbess"] translators: - ["Mariane Siqueira Machado", "https://twitter.com/mariane_sm"] lang: pt-br -filename: learnswift.swift + --- Swift é uma linguagem de programação para desenvolvimento de aplicações no iOS e OS X criada pela Apple. Criada para @@ -388,13 +389,13 @@ if mySquare === mySquare { // Podem conter métodos do mesmo jeito que classes. enum Suit { - case Spades, Hearts, Diamonds, Clubs + case spades, hearts, diamonds, clubs func getIcon() -> String { switch self { - case .Spades: return "♤" - case .Hearts: return "♡" - case .Diamonds: return "♢" - case .Clubs: return "♧" + case .spades: return "♤" + case .hearts: return "♡" + case .diamonds: return "♢" + case .clubs: return "♧" } } } diff --git a/pt-br/typescript-pt.html.markdown b/pt-br/typescript-pt.html.markdown index f072b257..ed76959c 100644 --- a/pt-br/typescript-pt.html.markdown +++ b/pt-br/typescript-pt.html.markdown @@ -8,20 +8,13 @@ translators: lang: pt-br --- -TypeScript is a language that aims at easing development of large scale applications written in JavaScript. -TypeScript adds common concepts such as classes, modules, interfaces, generics and (optional) static typing to JavaScript. -It is a superset of JavaScript: all JavaScript code is valid TypeScript code so it can be added seamlessly to any project. The TypeScript compiler emits JavaScript. - -This article will focus only on TypeScript extra syntax, as opposed to [JavaScript] (../javascript/). - - Typescript é uma linguagem que visa facilitar o desenvolvimento de aplicações em grande escala escritos em JavaScript. Typescript acrescenta conceitos comuns como classes, módulos, interfaces, genéricos e (opcional) tipagem estática para JavaScript. -É um super conjunto de JavaScript: todo o código JavaScript é o código do texto dactilografado válido para que possa ser adicionados diretamente a qualquer projeto. O compilador emite typescript JavaScript. +É um super conjunto de JavaScript: todo o código JavaScript é TypeScript válido então ele pode ser adicionado diretamente a qualquer projeto. O compilador emite TypeScript JavaScript. -Este artigo irá se concentrar apenas em texto datilografado sintaxe extra, ao contrário de [JavaScript](javascript-pt.html.markdown). +Este artigo irá se concentrar apenas na sintaxe extra do TypeScript, ao contrário de [JavaScript](javascript-pt.html.markdown). -Para testar compilador do texto datilografado, de cabeça para o [Parque](http://www.typescriptlang.org/Playground), onde você vai ser capaz de escrever código, ter auto conclusão e ver diretamente o JavaScript emitida. +Para testar o compilador TypeScript, vá para o [Playground](http://www.typescriptlang.org/Playground), onde você vai ser capaz de escrever código, ter auto conclusão e ver diretamente o JavaScript emitido. ```js // Existem 3 tipos básicos no TypeScript @@ -29,7 +22,7 @@ var isDone: boolean = false; var lines: number = 42; var name: string = "Anders"; -// Quando é impossível saber, há o "Qualquer" tipo +// Quando é impossível saber, há o tipo "Qualquer" var notSure: any = 4; notSure = "maybe a string instead"; notSure = false; // Ok, definitivamente um boolean @@ -51,13 +44,13 @@ function bigHorribleAlert(): void { // Funções são cidadãos de primeira classe, apoiar a sintaxe lambda "seta gordura" e // Tipo de uso inferência -// A seguir são equivalentes, a mesma assinatura será inferido pelo -// Compilador, e mesmo JavaScript será emitido +// A seguir são equivalentes, a mesma assinatura será inferida pelo +// Compilador, e o mesmo JavaScript será emitido var f1 = function(i: number): number { return i * i; } -// Tipo de retorno inferida +// Tipo de retorno inferido var f2 = function(i: number) { return i * i; } var f3 = (i: number): number => { return i * i; } -// Tipo de retorno inferida +// Tipo de retorno inferido var f4 = (i: number) => { return i * i; } // Tipo de retorno inferido, one-liner significa nenhuma palavra-chave retorno necessário var f5 = (i: number) => i * i; @@ -72,7 +65,7 @@ interface Person { move(): void; } -// Objeto que implementa a "Pessoa" Interface +// Objeto que implementa a Interface "Pessoa" // Pode ser tratado como uma pessoa desde que tem o nome e mover propriedades var p: Person = { name: "Bobby", move: () => {} }; // Os objetos que têm a propriedade opcional: @@ -95,7 +88,7 @@ class Point { // Propriedades x: number; - // Construtor - the public/private keywords in this context will generate + // Construtor - as palavras-chave public/private nesse contexto irão gerar // o código clichê para a propriedade e a inicialização no // construtor. // Neste exemplo, "y" será definida como "X" é, mas com menos código diff --git a/pt-br/vim-pt.html.markdown b/pt-br/vim-pt.html.markdown index 4f70079a..cc304381 100644 --- a/pt-br/vim-pt.html.markdown +++ b/pt-br/vim-pt.html.markdown @@ -5,15 +5,16 @@ contributors: - ["RadhikaG", "https://github.com/RadhikaG"] translators: - ["David Lima", "https://github.com/davelima"] + - ["Raul Almeida", "https://github.com/almeidaraul"] lang: pt-br filename: LearnVim-pt.txt --- -[Vim](www.vim.org) +[Vim](http://www.vim.org) (Vi IMproved - Vi Melhorado) é um clone do editor vi para Unix. Ele é um editor de texto projetado para ter velocidade e produtividade, e está presente -na maioria dos systemas UNIX. O editor tem um grande número de atalhos de teclado +na maioria dos sistemas UNIX. O editor tem um grande número de atalhos de teclado para agilizar a navegação para pontos específicos no arquivo, além de edição rápida. ## Navegação do Vim: o básico @@ -24,8 +25,9 @@ para agilizar a navegação para pontos específicos no arquivo, além de ediç :w # Salva o arquivo atual :wq # Salva o arquivo e fecha o vim :q! # Fecha o vim e descarta as alterações no arquivo + # ! depois de qualquer comando força a sua execução # ! *força* :q a executar, fechando o vim sem salvar antes - :x # Salvar o arquivo e fechao vim (atalho para :wq) + :x # Salva o arquivo e fecha o vim (atalho para :wq) u # Desfazer CTRL+R # Refazer @@ -62,7 +64,7 @@ para agilizar a navegação para pontos específicos no arquivo, além de ediç # Movendo por palavras - w # Move o cursor uma palavra a diante + w # Move o cursor uma palavra adiante b # Move o cursor uma palavra atrás e # Move o cursor ao fim da palavra atual @@ -158,7 +160,15 @@ Alguns exemplos importantes de 'Verbos', 'Modificadores' e 'Nomes': :earlier 15m # Reverte o documento para como ele estava há 15 minutos atrás :later 15m # Reverte o comando acima ddp # Troca linhas consecutivas de posição, dd e depois p + xp # Permuta caractere atual e o seguinte + Xp # Permuta caractere atual e o anterior . # Repete a última ação + + # Em geral, o usuário pode associar um comando em maísculas (exemplo: D) com + # "executar este comando até o final da linha" + + # Usar a tecla de um comando duas vezes geralmente significa executar este + # comando sobre toda a linha (exemplo: dd apaga a linha inteira) ``` ## Macros @@ -172,6 +182,7 @@ exatamente a mesma sequencia de ações e comandos na seleção atual. qa # Inicia a gravação de uma macro chamado 'a' q # Para a gravação @a # Executa a macro + @@ # Executa a última macro executada ``` ### Configurando o ~/.vimrc diff --git a/pt-br/visualbasic-pt.html.markdown b/pt-br/visualbasic-pt.html.markdown index 76cca567..2a7205cd 100644 --- a/pt-br/visualbasic-pt.html.markdown +++ b/pt-br/visualbasic-pt.html.markdown @@ -8,16 +8,16 @@ lang: pt-br filename: learnvisualbasic-pt.vb --- -```vb +``` Module Module1 module Module1 Sub Main () ' Uma visão geral de console de aplicativos do Visual Basic antes de - ' mergulharmos mais profundamente na linguagem + ' mergulharmos mais profundamente na linguagem. ' Aspas simples começam comentários. - ' Para Navegar este tutorial dentro do compilador do Visual Basic, + ' Para navegar neste tutorial dentro do compilador do Visual Basic, ' eu criei um sistema de navegação. ' Este sistema de navegação vai ser explicado conforme avançarmos no ' tutorial, e você vai entender o que isso significa. @@ -93,16 +93,16 @@ module Module1 Private Sub HelloWorldInput () Console.Title = " Olá Mundo YourName | Saiba X em Y Minutes" ' Variáveis - 'Os dados inseridos por um usuário precisa ser armazenada . + 'Os dados inseridos por um usuário precisam ser armazenados. ' As variáveis também começar com um Dim e terminar com um Como VariableType . - ' Neste tutorial, nós queremos saber o que o seu nome, e faça o programa + ' Neste tutorial, nós queremos saber qual é o seu nome, e faça o programa ' Responder ao que é dito. Nome de usuário Dim As String " Nós usamos string como string é uma variável de texto baseado . Console.WriteLine (" Olá, Qual é o seu nome? ") ' Peça ao usuário seu nome. - username = Console.ReadLine () ' armazena o nome usuários. - Console.WriteLine (" Olá " + nome do usuário) " A saída é Olá ' Seu nome ' + username = Console.ReadLine () ' armazena o nome do usuário. + Console.WriteLine (" Olá " + username) ' A saída é "Olá < seu nome >". Console.ReadLine () ' Outsputs acima. ' O código acima irá lhe fazer uma pergunta seguiu imprimindo sua resposta. " Outras variáveis incluem Integer e usamos inteiro para números inteiros. diff --git a/pt-br/whip-pt.html.markdown b/pt-br/whip-pt.html.markdown new file mode 100644 index 00000000..b11faf28 --- /dev/null +++ b/pt-br/whip-pt.html.markdown @@ -0,0 +1,247 @@ +--- +language: whip +contributors: + - ["Tenor Biel", "http://github.com/L8D"] + - ["Saurabh Sandav", "http://github.com/SaurabhSandav"] +author: Tenor Biel +author_url: http://github.com/L8D +translators: + - ["Paulo Henrique Rodrigues Pinheiro", "https://github.com/paulohrpinheiro"] +lang: pt-br +filename: whip-pt.lisp +--- + +Whip é um dialeto de Lisp feito para construir scripts e trabalhar com +conceitos mais simples. +Ele também copia muitas funções e sintaxe de Haskell (uma linguagem não correlata) + +Esse documento foi escrito pelo próprio autor da linguagem. Então é isso. + +```scheme +; Comentário são como em Lisp. Pontos-e-vírgulas... + +; A maioria das declarações de primeiro nível estão dentro de "listas" +; que nada mais são que coisas entre parênteses separadas por espaços em branco +nao_é_uma_lista +(uma lista) + +;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; +; 1. Números, texto e operadores + +; Whip tem um tipo numérico (que é um double de 64 bits IEE 754, do JavaScript) +3 ; => 3 +1.5 ; => 1.5 + +; Funções são chamadas se elas são o primeiro elemento em uma lista +(funcao_chamada argumentos) + +; A maioria das operações são feitas com funções +; Todas as funções aritméticas básicas são bem diretas +(+ 1 1) ; => 2 +(- 2 1) ; => 1 +(* 1 2) ; => 2 +(/ 2 1) ; => 2 +; até mesmo o módulo +(% 9 4) ; => 1 +; Divisão não inteira ao estilo JavaScript. +(/ 5 2) ; => 2.5 + +; Aninhamento de listas funciona como esperado. +(* 2 (+ 1 3)) ; => 8 + +; Há um tipo boleano. +true +false + +; Textos são criados com ". +"Hello, world" + +; Caracteres são criados com '. +'a' + +; Para negação usa-se a função 'not'. +(not true) ; => false +(not false) ; => true + +; Mas a maioria das funções não-haskell tem atalhos +; o atalho para "não" é um '!'. +(! (! true)) ; => true + +; Igualdade é `equal` ou `=`. +(= 1 1) ; => true +(equal 2 1) ; => false + +; Por exemplo, desigualdade pode ser verificada combinando as funções +;`not` e `equal`. +(! (= 2 1)) ; => true + +; Mais comparações +(< 1 10) ; => true +(> 1 10) ; => false +; e suas contra partes para texto. +(lesser 1 10) ; => true +(greater 1 10) ; => false + +; Texto pode ser concatenado com +. +(+ "Hello " "world!") ; => "Hello world!" + +; Você pode usar as características comparativas do JavaScript. +(< 'a' 'b') ; => true +; ... e coerção de tipos +(= '5' 5) + +; As funções `at` ou `@` acessarão caracteres de um texto, começando em 0. +(at 0 'a') ; => 'a' +(@ 3 "foobar") ; => 'b' + +; Também existem as variáveis `null` e `undefined`. +null ; usada para indicar a ausência de algum valor +undefined ; usada para indicar que um valor não foi informado + +;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; +; 2. Variáveis, matrizes e dicionários + +; Variáveis são declaradas com as funções `def` ou `let`. +; Variáveis que não tiveram valor atribuído serão `undefined`. +(def some_var 5) +; `def` deixará a variável no contexto global. +; `let` deixará a variável no contexto local, e tem uma sintaxe estranha. +(let ((a_var 5)) (+ a_var 5)) ; => 10 +(+ a_var 5) ; = undefined + 5 => undefined + +; Matrizes são listas de valores de qualquer tipo. +; Elas basicamente são listas sem funções no início +(1 2 3) ; => [1, 2, 3] (sintaxe JavaScript) + +; Dicionários em Whip são o equivalente a 'object' em JavaScript ou +; 'dict' em python ou 'hash' em Ruby: eles são uma coleção desordenada +de pares chave-valor. +{"key1" "value1" "key2" 2 3 3} + +; Chaves podem ser apenas identificadores, números ou texto. +(def my_dict {my_key "my_value" "my other key" 4}) +; Mas em Whip, dicionários são parceados como: valor, espaço, valor; +; com mais espaço entre cada. Então isso significa que +{"key" "value" +"another key" +1234 +} +é avaliado da mesma forma que +{"key" "value" "another key" 1234} + +; Dicionários podem ser acessados usando a função `at` +; (como em texto e listas) +(@ "my other key" my_dict) ; => 4 + +;;;;;;;;;;;;;;;;;;;;;;;;;;;;; +; 3. Lógica e controle de fluxo + +; A função `if` é muito simples, ainda que muito diferente do que em muitas +linguagens imperativas. +(if true "returned if first arg is true" "returned if first arg is false") +; => "returned if first arg is true" + +; E por conta do legado operador ternário +; `?` é o atalho não utilizado para `if`. +(? false true false) ; => false + +; `both` é uma declaração lógica `and`, e `either` é o `or` lógico. +(both true true) ; => true +(both true false) ; => false +(either true false) ; => true +(either false false) ; => false +; E seus atalhos são +; & => both +; ^ => either +(& true true) ; => true +(^ false true) ; => true + +;;;;;;;;; +; Lambdas + +; Lambdas em Whip são declaradas com as funções `lambda` ou `->`. +; E funções são na verdade lambdas com nomes. +(def my_function (-> (x y) (+ (+ x y) 10))) +; | | | | +; | | | valor retornado (com escopo contento argumentos) +; | | argumentos +; | declaração de funções lambda +; | +; nome do lambda a ser declarado + +(my_function 10 10) ; = (+ (+ 10 10) 10) => 30 + +; Obviamente, todos os lambdas por definição são anônimos e +; tecnicamente sempre usados anonimamente. Redundância. +((lambda (x) x) 10) ; => 10 + +;;;;;;;;;;;;;;;; +; Comprehensions + +; `range` or `..` geram uma lista dos números para +; cada número entre seus dois argumentos. +(range 1 5) ; => (1 2 3 4 5) +(.. 0 2) ; => (0 1 2) + +; `map` aplica seu primeiro argumento (que deve ser um lambda/função) +; a cada item dos argumentos seguintes (que precisa ser uma lista) +(map (-> (x) (+ x 1)) (1 2 3)) ; => (2 3 4) + +; Reduce +(reduce + (.. 1 5)) +; equivalente a +((+ (+ (+ 1 2) 3) 4) 5) + +; Nota: map e reduce não possuem atalhos + +; `slice` ou `\` é similar ao .slice() do JavaScript +; mas veja que ele pega uma lista como primeiro argumento, não o último. +(slice (.. 1 5) 2) ; => (3 4 5) +(\ (.. 0 100) -5) ; => (96 97 98 99 100) + +; `append` ou `<<` são auto explicativos +(append 4 (1 2 3)) ; => (1 2 3 4) +(<< "bar" ("foo")) ; => ("foo" "bar") + +; Length é auto explicativo. +(length (1 2 3)) ; => 3 +(_ "foobar") ; => 6 + +;;;;;;;;;;;;;;; +; Delicadezas Haskell + +; Primeiro item de uma lista +(head (1 2 3)) ; => 1 +; Pega do segundo ao último elemento de uma lista +(tail (1 2 3)) ; => (2 3) +; Último item de uma lista +(last (1 2 3)) ; => 3 +; Contrário de `tail` +(init (1 2 3)) ; => (1 2) +; Pega do primeiro até o elemento especificado da lista +(take 1 (1 2 3 4)) ; (1 2) +; Contrário de `take` +(drop 1 (1 2 3 4)) ; (3 4) +; Menor valor em uma lista +(min (1 2 3 4)) ; 1 +; Maior valor em uma lista +(max (1 2 3 4)) ; 4 +; Verifica se o valor está em uma lista ou objeto +(elem 1 (1 2 3)) ; true +(elem "foo" {"foo" "bar"}) ; true +(elem "bar" {"foo" "bar"}) ; false +; Inverte a ordem de uma lista +(reverse (1 2 3 4)) ; => (4 3 2 1) +; Verifica se o valor é par ou ímpar +(even 1) ; => false +(odd 1) ; => true +; Separa um texto cortando por espaço em branco +(words "foobar nachos cheese") ; => ("foobar" "nachos" "cheese") +; Junta lista de textos +(unwords ("foo" "bar")) ; => "foobar" +; Sucessor e predecessor +(pred 21) ; => 20 +(succ 20) ; => 21 +``` + +Para mais informação, verifique o [repositório](http://github.com/L8D/whip) diff --git a/pt-br/xml-pt.html.markdown b/pt-br/xml-pt.html.markdown index f347f8ef..6710b387 100644 --- a/pt-br/xml-pt.html.markdown +++ b/pt-br/xml-pt.html.markdown @@ -10,8 +10,7 @@ lang: pt-br XML é uma linguagem de marcação projetada para armazenar e transportar dados. -Ao contrário de HTML, XML não especifica como exibir ou formatar os dados, -basta carregá-lo. +Ao contrário de HTML, XML não especifica como exibir ou formatar os dados, apenas o transporta. * Sintaxe XML diff --git a/pt-br/yaml-pt.html.markdown b/pt-br/yaml-pt.html.markdown index 341ae675..21e9b4bb 100644 --- a/pt-br/yaml-pt.html.markdown +++ b/pt-br/yaml-pt.html.markdown @@ -1,7 +1,7 @@ --- language: yaml contributors: - - ["Adam Brenecki", "https://github.com/adambrenecki"] + - ["Leigh Brenecki", "https://github.com/adambrenecki"] translators: - ["Rodrigo Russo", "https://github.com/rodrigozrusso"] filename: learnyaml-pt.yaml @@ -11,12 +11,10 @@ lang: pt-br YAML é uma linguagem de serialização de dados projetado para ser diretamente gravável e legível por seres humanos. -É um estrito subconjunto de JSON, com a adição de sintaticamente -novas linhas e recuo significativos, como Python. Ao contrário de Python, no entanto, -YAML não permite caracteres de tabulação literais em tudo. +É um superconjunto de JSON, com a adição de identação e quebras de linhas sintaticamente significativas, como Python. Ao contrário de Python, entretanto, YAML não permite o caracter literal tab para identação. ```yaml -# Commentários em YAML são como este. +# Comentários em YAML são como este. ################### # TIPOS ESCALARES # @@ -35,7 +33,7 @@ chave com espaco: valor porem: "Uma string, entre aspas." "Chaves podem estar entre aspas tambem.": "É útil se você quiser colocar um ':' na sua chave." -# Seqüências de várias linhas podem ser escritos como um 'bloco literal' (utilizando |), +# Seqüências de várias linhas podem ser escritas como um 'bloco literal' (utilizando |), # ou em um 'bloco compacto' (utilizando '>'). bloco_literal: | Todo esse bloco de texto será o valor da chave 'bloco_literal', @@ -78,7 +76,7 @@ um_mapa_aninhado: # também permite tipos de coleção de chaves, mas muitas linguagens de programação # vão reclamar. -# Sequências (equivalente a listas ou arrays) semelhante à isso: +# Sequências (equivalente a listas ou arrays) semelhante a isso: uma_sequencia: - Item 1 - Item 2 @@ -120,7 +118,7 @@ datetime: 2001-12-15T02: 59: 43.1Z datetime_com_espacos 2001/12/14: 21: 59: 43.10 -5 Data: 2002/12/14 -# A tag !!binary indica que a string é na verdade um base64-encoded (condificado) +# A tag !!binary indica que a string é na verdade um base64-encoded (codificado) # representação de um blob binário. gif_file: !!binary | R0lGODlhDAAMAIQAAP//9/X17unp5WZmZgAAAOfn515eXvPz7Y6OjuDg4J+fn5 |