freeCodeCamp/guide/portuguese/certifications/coding-interview-prep/algorithms/no-repeats-please/index.md

9.4 KiB

title localeTitle
No Repeats Please Não repete por favor

:triangular_flag_on_post: Lembre-se de usar Read-Search-Ask se você ficar preso. Tente emparelhar o programa :busts_in_silhouette: e escreva seu próprio código :pencil:

:checkered_flag: Explicação do Problema:

Essa tarefa exige que retornemos o número total de permutações da string fornecida que não tem letras consecutivas repetidas. Deve ser assumido que todos os caracteres na string fornecida são únicos. Por exemplo, aab deve retornar 2 porque tem 6 permutações totais ( aab , aab , aba , aba , baa , baa ), mas apenas 2 delas ( aba e aba ) não têm a mesma letra (neste caso a ) recorrente.

Para conseguir isso, vamos ter que olhar para cada possível permutação de uma string. Existem várias maneiras de fazer isso. Uma questão de entrevista comum é a construção de uma função que coleta todas as permutações de uma string. Existem vários tutoriais disponíveis na internet sobre como fazer isso.

Métodos Potenciais Utilizados Como Solução

Método Recursivo

Essa tarefa pode ser assustadora mesmo depois de assistir a um tutorial. Para escrever uma solução recursiva, você desejará enviar a cada novo uso da função três entradas:

  1. Uma nova string (ou matriz de caracteres) que está sendo construída.
  2. Uma posição na sua nova string que será preenchida em seguida.
  3. Uma ideia de quais caracteres (mais especificamente posições) da string original ainda não foram usados.

O pseudo código será parecido com isto:

var str = ???; 
 permAlone(current position in original string, characters used already in original string, created string) { 
  if (current string is finished) { 
    print current string; 
  } else { 
    for (var i = 0; i < str.length; i++) { 
      if (str[i] has not been used) { 
        put str[i] into the current position of new string; 
        mark str[i] as used; 
        permAlone(current position in original string, characters used already in original string, created string); 
        remove str[i] as used because another branch in the tree for i + 1 will likely use it; 
      } 
    } 
  } 
 } 
 permAlone(0, nothing used yet, empty new string (or array the same size as str)); 

Outra maneira de pensar sobre esse problema é começar de um espaço vazio. Introduza a primeira letra do espaço. Este espaço irá agora conter a primeira sub-permutação. Aqui está um diagrama ilustrando a ideia:

diagrama

Método não recursivo
// An approach to introduce a new character to a permutation 
 var ch = '?'; 
 var source = ['?', '?', '?'];     // Current sub-permutation 
 var temp, dest = []; 
 
 for (var i = 0; i <= source.length; ++i) { 
  temp = source.slice(0);         // Copy the array 
  temp.splice(i, 0, ch);          // Insert the new character 
  dest.push(temp);                // Store the new sub-permutation 
 } 

Encontrar cada permutação poderia ser feito de forma não recursiva, incluindo o acima em uma função, tomando uma matriz de origem e retornando uma matriz de destino. Para cada letra da string de entrada, passe esse caractere, assim como a matriz retornada da chamada anterior da função.

Uma maneira de visualizar isso é considerando uma árvore que começa com o primeiro caractere da sua string:

Árvore de permutação

:speech_balloon: Sugestão: 1

  • A maneira mais fácil é usar o algoritmo de Heap para obter recursivamente uma lista de todas as permutações.

tente resolver o problema agora

:speech_balloon: Dica: 2

  • Depois de ter a lista, basta criar uma expressão regular para capturar os caracteres repetidos.

tente resolver o problema agora

:speech_balloon: Dica: 3

  • Você desejará ter as permutações como uma matriz de strings associadas, em vez de caracteres separados.

tente resolver o problema agora

Alerta de Spoiler!

sinal de aviso

Solução à frente!

:beginner: Solução básica de código:

function permAlone(str) { 
 
  // Create a regex to match repeated consecutive characters. 
  var regex = /(.)\1+/g; 
 
  // Split the string into an array of characters. 
  var arr = str.split(''); 
  var permutations = <a href='https://forum.freecodecamp.com/images/emoji/emoji_one/rocket.png?v=3 ":rocket:"' target='_blank' rel='nofollow'>]; 
  var tmp; 
 
  // Return 0 if str contains same character. 
  if (str.match(regex) !== null && str.match(regex)[0] === str) return 0; 
 
  // Function to swap variables' content. 
  function swap(index1, index2) { 
    tmp = arr[index1]; 
    arr[index1] = arr[index2]; 
    arr[index2] = tmp; 
  } 
 
  // Generate arrays of permutations using the algorithm. 
  function generate(int) { 
    if (int === 1) { 
      // Make sure to join the characters as we create  the permutation arrays 
      permutations.push(arr.join('')); 
    } else { 
      for (var i = 0; i != int; ++i) { 
        generate(int - 1); 
        swap(int % 2 ? 0 : i, int - 1); 
      } 
    } 
  } 
 
  generate(arr.length); 
 
  // Filter the array of repeated permutations. 
  var filtered = permutations.filter(function(string) { 
    return !string.match(regex); 
  }); 
 
  // Return how many have no repetitions. 
  return filtered.length; 
 } 
 
 // Test here. 
 permAlone('aab'); 

:rocket: Executar código

Explicação do código:

  • regex contém a expressão regular para coincidir com caracteres consecutivos repetidos.
  • A string str é dividida em uma matriz de caracteres, arr .
  • 0 é retornado se str contiver os mesmos caracteres.
  • A função swap() é usada para trocar o conteúdo do conteúdo de duas variáveis.
  • O próximo bloco de código usa o algoritmo de Heap para gerar matrizes de permutações em permutações .
  • A variável filtrada filtra as permutações para incluir apenas permutações não repetidas.
  • filtered.length retorna o número total de permutações da string fornecida que não tem letras consecutivas repetidas.

:clipboard: NOTAS PARA CONTRIBUIÇÕES:

  • :warning: NÃO adicione soluções semelhantes às soluções existentes. Se você acha que é semelhante, mas melhor , tente mesclar (ou substituir) a solução semelhante existente.
  • Adicione uma explicação da sua solução.
  • Categorize a solução em uma das seguintes categorias - Básica , Intermediária e Avançada . :traffic_light:
  • Por favor, adicione seu nome de usuário somente se você adicionou qualquer conteúdo principal relevante . ( :warning: NÃO remova nenhum nome de usuário existente )

Vejo :point_right: Wiki Challenge Solution Template para referência.