Merge branch 'master' into linear-prime-sieve

This commit is contained in:
Sandeep Satheesh 2019-01-26 23:21:16 +05:30 committed by GitHub
commit 1d378aebc6
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
55 changed files with 2200 additions and 2622 deletions

View File

@ -1,10 +1,10 @@
# Algoritmos JavaScript y Estructuras de Datos
# Algoritmos y Estructuras de Datos en JavaScript
[![Build Status](https://travis-ci.org/trekhleb/javascript-algorithms.svg?branch=master)](https://travis-ci.org/trekhleb/javascript-algorithms)
[![codecov](https://codecov.io/gh/trekhleb/javascript-algorithms/branch/master/graph/badge.svg)](https://codecov.io/gh/trekhleb/javascript-algorithms)
Este repositorio contiene ejemplos basados en JavaScript de muchos
algoritmos populares y estructuras de datos.
algoritmos y estructuras de datos populares.
Cada algoritmo y estructura de datos tiene su propio LÉAME con explicaciones relacionadas y
enlaces para lecturas adicionales (incluyendo algunas a vídeos de YouTube).
@ -14,36 +14,40 @@ _Léelo en otros idiomas:_
[_简体中文_](README.zh-CN.md),
[_繁體中文_](README.zh-TW.md),
[_한국어_](README.ko-KR.md),
[_日本語_](README.ja-JP.md),
[_Polski_](README.pl-PL.md),
[_Français_](README.fr-FR.md),
[_Português_](README.pt-BR.md)
*☝ Nótese que este proyecto está pensado con fines de aprendizaje e investigación,
y **no** para ser usado en producción.*
## Estructuras de Datos
Una estructura de datos es una forma particular de organizar y almacenar datos en un ordenador para que pueda
y modificarse de forma eficiente. Más concretamente, una estructura de datos es un conjunto de datos
los valores, las relaciones entre ellos y las funciones u operaciones que se pueden aplicar a
Una estructura de datos es una forma particular de organizar y almacenar datos en un ordenador para que puedan accederse
y modificarse de forma eficiente. Más concretamente, una estructura de datos es un conjunto de valores
de datos, las relaciones entre ellos y las funciones u operaciones que se pueden aplicar a
los datos.
`P` - Principiante, `A` - Avanzado
* `P` [Lista Enlazada](src/data-structures/linked-list)
* `P` [Lista Doblemente Enlazada](src/data-structures/doubly-linked-list)
* `P` [Lista enlazada](src/data-structures/linked-list)
* `P` [Lista doblemente enlazada](src/data-structures/doubly-linked-list)
* `P` [Cola](src/data-structures/queue)
* `P` [Pila - Stack](src/data-structures/stack)
* `P` [Hash Table](src/data-structures/hash-table)
* `P` [Pila - Heap](src/data-structures/heap)
* `P` [Cola de Prioridad](src/data-structures/priority-queue)
* `P` [Pila](src/data-structures/stack)
* `P` [Tabla hash](src/data-structures/hash-table)
* `P` [Heap](src/data-structures/heap) - versiones máx y mín
* `P` [Cola de prioridad](src/data-structures/priority-queue)
* `A` [Trie](src/data-structures/trie)
* `A` [Arbol](src/data-structures/tree)
* `A` [Arbol de busqueda binaria](src/data-structures/tree/binary-search-tree)
* `A` [Arbol AVL ](src/data-structures/tree/avl-tree)
* `A` [Árbol](src/data-structures/tree)
* `A` [Árbol de búsqueda binaria](src/data-structures/tree/binary-search-tree)
* `A` [Árbol AVL](src/data-structures/tree/avl-tree)
* `A` [Árbol Rojo-Negro](src/data-structures/tree/red-black-tree)
* `A` [Árbol de segmentos](src/data-structures/tree/segment-tree) - con ejemplos de consultas de rango mín/máx/suma
* `A` [Arbol de Fenwick ](src/data-structures/tree/fenwick-tree) (Árbol binario indexado)
* `A` [Grafo](src/data-structures/graph) (con dirección y sin dirección)
* `A` [Conjunto disjunto](src/data-structures/disjoint-set)
* `A` [Filtro Bloom](src/data-structures/bloom-filter)
* `A` [Árbol de Fenwick](src/data-structures/tree/fenwick-tree) (Árbol binario indexado)
* `A` [Grafo](src/data-structures/graph) (dirigido y no dirigido)
* `A` [Conjuntos disjuntos](src/data-structures/disjoint-set)
* `A` [Filtro de Bloom](src/data-structures/bloom-filter)
## Algoritmos
@ -54,137 +58,147 @@ definen con precisión una secuencia de operaciones.
### Algoritmos por Tema
* **Matematica**
* `P` [Manipulacion de bits](src/algorithms/math/bits) - setear/obtener/actualizar/limpiar bits, multiplication/division por dos, hacer negativo, etc.
* **Matemáticas**
* `P` [Manipulación de bits](src/algorithms/math/bits) - asignar/obtener/actualizar/limpiar bits, multiplicación/división por dos, hacer negativo, etc.
* `P` [Factorial](src/algorithms/math/factorial)
* `P` [Numero de Fibonacci](src/algorithms/math/fibonacci)
* `P` [Prueba de Primacia](src/algorithms/math/primality-test) (metodo de division de prueba)
* `P` [Algoritmo Euclideo](src/algorithms/math/euclidean-algorithm) - Calcular el maximo comun divisor (MCD)
* `P` [Minimo comun multiplo](src/algorithms/math/least-common-multiple) (MCM)
* `P` [Tamiz de Eratosthenes](src/algorithms/math/sieve-of-eratosthenes) - encontrar todos los números primos hasta cualquier límite dado
* `P` [Es la potencia de dos](src/algorithms/math/is-power-of-two) - comprueba si el número es la potencia de dos (algoritmos ingenuos y de bits)
* `P` [Triangulo de Pascal](src/algorithms/math/pascal-triangle)
* `A` [Particion Entera](src/algorithms/math/integer-partition)
* `A` [Algortimo π de Liu Hui ](src/algorithms/math/liu-hui) - aproximado π cálculos basados en N-gons
* `P` [Número de Fibonacci](src/algorithms/math/fibonacci)
* `P` [Prueba de primalidad](src/algorithms/math/primality-test) (método de división de prueba)
* `P` [Algoritmo de Euclides](src/algorithms/math/euclidean-algorithm) - calcular el Máximo común divisor (MCD)
* `P` [Mínimo común múltiplo](src/algorithms/math/least-common-multiple) (MCM)
* `P` [Criba de Eratóstenes](src/algorithms/math/sieve-of-eratosthenes) - encontrar todos los números primos hasta un límite dado
* `P` [Es una potencia de dos?](src/algorithms/math/is-power-of-two) - comprobar si el número es una potencia de dos (algoritmos ingenuos y de bits)
* `P` [Triángulo de Pascal](src/algorithms/math/pascal-triangle)
* `P` [Números complejos](src/algorithms/math/complex-number) - números complejos y operaciones con ellos
* `P` [Radianes & Grados](src/algorithms/math/radian) - conversión de radianes a grados y viceversa
* `P` [Exponenciación rápida](src/algorithms/math/fast-powering)
* `A` [Partición entera](src/algorithms/math/integer-partition)
* `A` [Algortimo π de Liu Hui](src/algorithms/math/liu-hui) - aproximar el cálculo de π basado en polígonos de N lados
* `A` [Transformada discreta de Fourier](src/algorithms/math/fourier-transform) - descomponer una función de tiempo (señal) en las frecuencias que la componen
* **Conjuntos**
* `P` [Producto Cartesiano](src/algorithms/sets/cartesian-product) - producto de múltiples conjuntos
* `P` [Producto cartesiano](src/algorithms/sets/cartesian-product) - producto de múltiples conjuntos
* `P` [Permutación de FisherYates](src/algorithms/sets/fisher-yates) - permutación aleatoria de una secuencia finita
* `A` [Conjunto Potencia](src/algorithms/sets/power-set) - todos los subconjuntos de un conjunto
* `A` [Conjunto potencia](src/algorithms/sets/power-set) - todos los subconjuntos de un conjunto
* `A` [Permutaciones](src/algorithms/sets/permutations) (con y sin repeticiones)
* `A` [Combinaciones](src/algorithms/sets/combinations) (con y sin repeticiones)
* `A` [Subsecuencia Común más Larga](src/algorithms/sets/longest-common-subsequence) (SCL)
* `A` [Subsecuencia Creciente más Larga](src/algorithms/sets/longest-increasing-subsequence)
* `A` [Supersequencia Común Más Corta](src/algorithms/sets/shortest-common-supersequence) (SCS)
* `A` [Problema de la Mochila](src/algorithms/sets/knapsack-problem) - "0/1" y unos sin consolidar
* `A` [Maxima Subarreglo](src/algorithms/sets/maximum-subarray) - versiones de "Fuerza Bruta" y "Programación Dinámica" ( de Kadane's)
* `A` [Suma Combinada](src/algorithms/sets/combination-sum) - encuentra todas las combinaciones que forman una suma específica.
* **Cadenas de Caracteres**
* `A` [Subsecuencia común más larga](src/algorithms/sets/longest-common-subsequence) (LCS)
* `A` [Subsecuencia creciente más larga](src/algorithms/sets/longest-increasing-subsequence)
* `A` [Supersecuencia común más corta](src/algorithms/sets/shortest-common-supersequence) (SCS)
* `A` [Problema de la mochila](src/algorithms/sets/knapsack-problem) - "0/1" y "sin límite"
* `A` [Máximo subarreglo](src/algorithms/sets/maximum-subarray) - versiones de "fuerza bruta" y "programación dinámica" (de Kadane)
* `A` [Suma combinada](src/algorithms/sets/combination-sum) - encuentra todas las combinaciones que forman una suma específica
* **Cadenas de caracteres**
* `P` [Distancia de Hamming](src/algorithms/string/hamming-distance) - número de posiciones en las que los símbolos son diferentes
* `A` [Distancia de Levenshtein](src/algorithms/string/levenshtein-distance) - distancia mínima de edición entre dos secuencias
* `A` [Algoritmo Knuth-Morris-Prattm](src/algorithms/string/knuth-morris-pratt) (Algoritmo KMP) - búsqueda por subcadenas (coincidencia de patrones)
* `A` [Algoritmo Z](src/algorithms/string/z-algorithm) - úsqueda de subcadenas (coincidencia de patrones)
* `A` [Algoritmo de Rabin Karp ](src/algorithms/string/rabin-karp) - búsqueda por subcadenas
* `A` [Subcadena Común Más Larga](src/algorithms/string/longest-common-substring)
* `A` [Coincidencia por Expresiones Regulares](src/algorithms/string/regular-expression-matching)
* **Busquedas**
* `P` [Búsqueda Lineal](src/algorithms/search/linear-search)
* `P` [Búsqueda de Salto](src/algorithms/search/jump-search) (o Búsqueda de Bloque) - búsqueda en una lista ordenada
* `A` [Algoritmo Knuth-Morris-Pratt](src/algorithms/string/knuth-morris-pratt) (Algoritmo KMP) - búsqueda de subcadenas (coincidencia de patrones)
* `A` [Algoritmo Z](src/algorithms/string/z-algorithm) - búsqueda de subcadenas (coincidencia de patrones)
* `A` [Algoritmo de Rabin Karp](src/algorithms/string/rabin-karp) - búsqueda de subcadenas
* `A` [Subcadena común más larga](src/algorithms/string/longest-common-substring)
* `A` [Coincidencia por expresiones regulares](src/algorithms/string/regular-expression-matching)
* **Búsquedas**
* `P` [Búsqueda lineal](src/algorithms/search/linear-search)
* `P` [Búsqueda de salto](src/algorithms/search/jump-search) (o Búsqueda de bloque) - búsqueda en una lista ordenada
* `P` [Búsqueda binaria](src/algorithms/search/binary-search) - búsqueda en una lista ordenada
* `P` [ Búsqueda por Interpolación](src/algorithms/search/interpolation-search) - búsqueda en una lista ordenada yd uniformemente distribuida
* `P` [Búsqueda por interpolación](src/algorithms/search/interpolation-search) - búsqueda en una lista ordenada uniformemente distribuida
* **Ordenamiento**
* `P` [Ordenamiento de Burbuja](src/algorithms/sorting/bubble-sort)
* `P` [Ordenamiento por Selección](src/algorithms/sorting/selection-sort)
* `P` [Ordenamiento por Inserción](src/algorithms/sorting/insertion-sort)
* `P` [ Ordenamiento en Pilas](src/algorithms/sorting/heap-sort)
* `P` [Ordenamiento por Fusion](src/algorithms/sorting/merge-sort)
* `P` [Ordenamiento de burbuja](src/algorithms/sorting/bubble-sort)
* `P` [Ordenamiento por selección](src/algorithms/sorting/selection-sort)
* `P` [Ordenamiento por inserción](src/algorithms/sorting/insertion-sort)
* `P` [Ordenamiento por Heap](src/algorithms/sorting/heap-sort)
* `P` [Ordenamiento por mezcla](src/algorithms/sorting/merge-sort)
* `P` [Quicksort](src/algorithms/sorting/quick-sort) - implementaciones in situ y no in situ
* `P` [Shellsort](src/algorithms/sorting/shell-sort)
* `P` [Clasificación de Recuento](src/algorithms/sorting/counting-sort)
* `P` [Ordenamiento por cuentas](src/algorithms/sorting/counting-sort)
* `P` [Ordenamiento Radix](src/algorithms/sorting/radix-sort)
* **Arboles**
* **Listas enlazadas**
* `P` [Recorrido directo](src/algorithms/linked-list/traversal)
* `P` [Recorrido inverso](src/algorithms/linked-list/reverse-traversal)
* **Árboles**
* `P` [Búsqueda en profundidad](src/algorithms/tree/depth-first-search) (DFS)
* `P` [Búsqueda en anchura](src/algorithms/tree/breadth-first-search) (BFS)
* **Grafos**
* `P` [Búsqueda en profundidad](src/algorithms/graph/depth-first-search) (DFS)
* `P` [Búsqueda en anchura](src/algorithms/graph/breadth-first-search) (BFS)
* `P` [Algoritmo de Kruskals](src/algorithms/graph/kruskal) - encontrar el árbol de expansión mínima (MST) para el grafo no dirigido ponderado
* `A` [Algoritmo de Dijkstra](src/algorithms/graph/dijkstra) - encontrar las trayectorias más cortas a todos los vértices del grafo desde un solo vértice
* `A` [Algoritmo de Bellman-Ford](src/algorithms/graph/bellman-ford) - encontrar las trayectorias más cortas a todos los vértices del gráfico desde un solo vértice
* `A` [Algortimo de Floyd-Warshall](src/algorithms/graph/floyd-warshall) - encuentra los caminos más cortos entre todos los pares de vértices
* `A` [Ciclo de detección](src/algorithms/graph/detect-cycle) - para gráficos dirigidos y no dirigidos (versiones basadas en DFS y Conjuntos Disjuntos)
* `A` [Algoritmo de Prim](src/algorithms/graph/prim) - encontrar el árbol de expansión mínima (MST) para una grafo no dirigido ponderada
* `A` [Clasificación topológica](src/algorithms/graph/topological-sorting) - método DFS
* `A` [Puntos de Articulación](src/algorithms/graph/articulation-points) - Algoritmo de Tarjan (basado en DFS)
* `A` [Puentes](src/algorithms/graph/bridges) - Algoritmo basado en DFS
* `A` [Senda Euleriana y un Circuito Euleriano](src/algorithms/graph/eulerian-path) - algoritmo de Fleury - Visite cada borde exactamente una vez
* `A` [Ciclo Hamiltoniano](src/algorithms/graph/hamiltonian-cycle) - visite cada vértice exactamente una vez
* `A` [Componentes Fuertemente Conectados](src/algorithms/graph/strongly-connected-components) - Algoritmo de Kosaraju
* `A` [Problema del Vendedor Itinerante](src/algorithms/graph/travelling-salesman) - la ruta más corta posible que visita cada ciudad y vuelve a la ciudad de origen
* `P` [Algoritmo de Kruskal](src/algorithms/graph/kruskal) - encontrar el árbol de cubrimiento mínimo (MST) para un grafo no dirigido ponderado
* `A` [Algoritmo de Dijkstra](src/algorithms/graph/dijkstra) - encontrar los caminos más cortos a todos los vértices del grafo desde un solo vértice
* `A` [Algoritmo de Bellman-Ford](src/algorithms/graph/bellman-ford) - encontrar los caminos más cortos a todos los vértices del grafo desde un solo vértice
* `A` [Algortimo de Floyd-Warshall](src/algorithms/graph/floyd-warshall) - encontrar los caminos más cortos entre todos los pares de vértices
* `A` [Detectar ciclos](src/algorithms/graph/detect-cycle) - para grafos dirigidos y no dirigidos (versiones basadas en DFS y conjuntos disjuntos)
* `A` [Algoritmo de Prim](src/algorithms/graph/prim) - encontrar el árbol de cubrimiento mínimo (MST) para un grafo no dirigido ponderado
* `A` [Ordenamiento topológico](src/algorithms/graph/topological-sorting) - método DFS
* `A` [Puntos de articulación](src/algorithms/graph/articulation-points) - algoritmo de Tarjan (basado en DFS)
* `A` [Puentes](src/algorithms/graph/bridges) - algoritmo basado en DFS
* `A` [Camino euleriano y circuito euleriano](src/algorithms/graph/eulerian-path) - algoritmo de Fleury - visitar cada arista exactamente una vez
* `A` [Ciclo hamiltoniano](src/algorithms/graph/hamiltonian-cycle) - visitar cada vértice exactamente una vez
* `A` [Componentes fuertemente conexos](src/algorithms/graph/strongly-connected-components) - algoritmo de Kosaraju
* `A` [Problema del viajante](src/algorithms/graph/travelling-salesman) - la ruta más corta posible que visita cada ciudad y vuelve a la ciudad de origen
* **Criptografia**
* `P` [Hash Polinomial](src/algorithms/cryptography/polynomial-hash) - función de hash rodante basada en polinomio
* **Sin Categoria**
* `P` [Torre de Hanoi](src/algorithms/uncategorized/hanoi-tower)
* `P` [Hash polinomial](src/algorithms/cryptography/polynomial-hash) - función de hash rodante basada en polinomio
* **Sin categoría**
* `P` [Torre de Hanói](src/algorithms/uncategorized/hanoi-tower)
* `P` [Rotación de matriz cuadrada](src/algorithms/uncategorized/square-matrix-rotation) - algoritmo in situ
* `P` [Juego de los saltos](src/algorithms/uncategorized/jump-game) - retroceso, programación dinámica (de arriba hacia abajo + de abajo hacia arriba) y ejemplos codiciosos
* `P` [Caminos Unicos](src/algorithms/uncategorized/unique-paths) -etroceso, programación dinámica y ejemplos basados en el Triángulo de Pascal
* `P` [Terrazas Pluviales](src/algorithms/uncategorized/rain-terraces) - problema de atrapamiento de aguas pluviales (programación dinámica y versiones de fuerza bruta)
* `A` [Problema de N-Reinas](src/algorithms/uncategorized/n-queens)
* `A` [Una gira de Caballeros](src/algorithms/uncategorized/knight-tour)
* `P` [Juego de los saltos](src/algorithms/uncategorized/jump-game) - ejemplos de backtracking, programación dinámica (de arriba hacia abajo + de abajo hacia arriba) y voraces
* `P` [Caminos únicos](src/algorithms/uncategorized/unique-paths) - ejemplos de backtracking, programación dinámica y basados en el Triángulo de Pascal
* `P` [Terrazas pluviales](src/algorithms/uncategorized/rain-terraces) - el problema de la retención del agua de lluvia (programación dinámica y fuerza bruta)
* `A` [Problema de las N Reinas](src/algorithms/uncategorized/n-queens)
* `A` [Problema del caballo (Knight tour)](src/algorithms/uncategorized/knight-tour)
### Algoritmos por Paradigma
### Algoritmos por paradigma
Un paradigma algorítmico es un método o enfoque genérico que subyace al diseño de una clase de algoritmos.
Es una abstracción superior a la noción de algoritmo, del mismo modo que un algoritmo es una abstracción superior a un programa de ordenador.
* **Fuerza Bruta** - mira todas las posibilidades y selecciona la mejor solución
* `P` [Busqueda Lienal](src/algorithms/search/linear-search)
* `P` [Terrazas Pluviales](src/algorithms/uncategorized/rain-terraces) - el problema de la retención del agua de lluvia
* `A` [Subcoleción maxima](src/algorithms/sets/maximum-subarray)
* `A` [Problema del Vendedor Itinerante](src/algorithms/graph/travelling-salesman) - la ruta más corta posible que visita cada ciudad y vuelve a la ciudad de origen
* **Codiciosos** - escoja la mejor opción en el momento actual, sin ninguna consideración para el futuro.
* `P` [El juego de los saltos](src/algorithms/uncategorized/jump-game)
* `A` [Problema de la Mochila no Consolidada](src/algorithms/sets/knapsack-problem)
* `A` [Algoritmo de Dijkstra](src/algorithms/graph/dijkstra) - encontrar la ruta más corta a todos los vértices del gráfico
* `A` [Algortimo de Prim](src/algorithms/graph/prim) - finding Minimum Spanning Tree (MST) for weighted undirected graph
* `A` [Algoritmo de Kruskal](src/algorithms/graph/kruskal) - encontrar el árbol de expansión mínima (MST) para una gráfica no dirigida ponderada
* **Divide y Venceras** - divide el problema en partes más pequeñas y luego resuelve esas partes.
* `P` [Búsqueda Binaria](src/algorithms/search/binary-search)
* `P` [Torre de Hanoi](src/algorithms/uncategorized/hanoi-tower)
* `P` [Triangulo de Pascal](src/algorithms/math/pascal-triangle)
* `P` [Algoritmo Euclideo](src/algorithms/math/euclidean-algorithm) - calcular el Maximo Comun Divisor (MCD)
* `P` [Clasificacion por Fusión](src/algorithms/sorting/merge-sort)
* `P` [Búsqueda lineal](src/algorithms/search/linear-search)
* `P` [Terrazas pluviales](src/algorithms/uncategorized/rain-terraces) - el problema de la retención del agua de lluvia
* `A` [Máximo subarreglo](src/algorithms/sets/maximum-subarray)
* `A` [Problema del viajante](src/algorithms/graph/travelling-salesman) - la ruta más corta posible que visita cada ciudad y vuelve a la ciudad de origen
* `A` [Transformada discreta de Fourier](src/algorithms/math/fourier-transform) - descomponer una función de tiempo (señal) en las frecuencias que la componen
* **Voraces** - escoge la mejor opción en el momento actual, sin ninguna consideración sobre el futuro
* `P` [Juego de los saltos](src/algorithms/uncategorized/jump-game)
* `A` [Problema de la mochila sin límite](src/algorithms/sets/knapsack-problem)
* `A` [Algoritmo de Dijkstra](src/algorithms/graph/dijkstra) - encontrar los caminos más cortos a todos los vértices del grafo desde un solo vértice
* `A` [Algortimo de Prim](src/algorithms/graph/prim) - encontrar el árbol de cubrimiento mínimo (MST) para un grafo no dirigido ponderado
* `A` [Algoritmo de Kruskal](src/algorithms/graph/kruskal) - encontrar el árbol de cubrimiento mínimo (MST) para un grafo no dirigido ponderado
* **Divide y Vencerás** - divide el problema en partes más pequeñas y luego resuelve esas partes
* `P` [Búsqueda binaria](src/algorithms/search/binary-search)
* `P` [Torre de Hanói](src/algorithms/uncategorized/hanoi-tower)
* `P` [Triángulo de Pascal](src/algorithms/math/pascal-triangle)
* `P` [Algoritmo de Euclides](src/algorithms/math/euclidean-algorithm) - calcular el Máximo Común Divisor (MCD)
* `P` [Ordenamiento por mezcla](src/algorithms/sorting/merge-sort)
* `P` [Quicksort](src/algorithms/sorting/quick-sort)
* `P` [Busqueda por Profundidad](src/algorithms/tree/depth-first-search) - (DFS)
* `P` [Busqueda por Anchura](src/algorithms/graph/depth-first-search) - (DFS)
* `P` [Juego de los Saltos](src/algorithms/uncategorized/jump-game)
* `P` [Búsqueda en profundidad (árboles)](src/algorithms/tree/depth-first-search) - (DFS)
* `P` [Búsqueda en profundidad (grafos)](src/algorithms/graph/depth-first-search) - (DFS)
* `P` [Juego de los saltos](src/algorithms/uncategorized/jump-game)
* `P` [Exponenciación rápida](src/algorithms/math/fast-powering)
* `A` [Permutaciones](src/algorithms/sets/permutations) - (con y sin repeticiones)
* `A` [Combinaciones](src/algorithms/sets/combinations) - (con y sin repeticiones)
* **Programacion Dinamica** - construya una solución usando sub-soluciones previamente encontradas
* `P` [Numero de Fibonacci](src/algorithms/math/fibonacci)
* `P` [Juego de los Saltos](src/algorithms/uncategorized/jump-game)
* `P` [Unicos Caminos](src/algorithms/uncategorized/unique-paths)
* `P` [Terrazas Pluviales](src/algorithms/uncategorized/rain-terraces) - el problema de la retención del agua de lluvia
* **Programación Dinámica** - construye una solución usando sub-soluciones previamente encontradas
* `P` [Número de Fibonacci](src/algorithms/math/fibonacci)
* `P` [Juego de los saltos](src/algorithms/uncategorized/jump-game)
* `P` [Caminos únicos](src/algorithms/uncategorized/unique-paths)
* `P` [Terrazas pluviales](src/algorithms/uncategorized/rain-terraces) - el problema de la retención del agua de lluvia
* `A` [Distancia de Levenshtein](src/algorithms/string/levenshtein-distance) - distancia mínima de edición entre dos secuencias
* `A` [Subsecuencia Comun más Larga](src/algorithms/sets/longest-common-subsequence) (LCS)
* `A` [Subcadena de Caracteres Comun más larga](src/algorithms/string/longest-common-substring)
* `A` [Subsecuencia Creciente más Larga](src/algorithms/sets/longest-increasing-subsequence)
* `A` [Susecuencia Comun más Corta](src/algorithms/sets/shortest-common-supersequence)
* `A` [0/1 Problema de la Mochila](src/algorithms/sets/knapsack-problem)
* `A` [Particion Entera](src/algorithms/math/integer-partition)
* `A` [Subarreglo Macima](src/algorithms/sets/maximum-subarray)
* `A` [Algoritmo de Bellman-Ford](src/algorithms/graph/bellman-ford) - encontrar el camino más corto a todos los vértices del grafo
* `A` [Floyd-Warshall Algorithm](src/algorithms/graph/floyd-warshall) - encuentra los caminos más cortos entre todos los pares de vértices
* `A` [Coincidencia por Expresiones regulares](src/algorithms/string/regular-expression-matching)
* **De Retorceso** - De manera similar a la fuerza bruta, trate de generar todas las soluciones posibles, pero cada vez que genere la siguiente solución, compruebe si cumple con todas las condiciones, y sólo entonces continúe generando soluciones posteriores. De lo contrario, retroceda y siga un camino diferente para encontrar una solución. Normalmente se utiliza la travesía del espacio estatal.
* `P` [Juego de Saltos](src/algorithms/uncategorized/jump-game)
* `P` [Camino Unico](src/algorithms/uncategorized/unique-paths)
* `A` [Ciclo Hamiltoniano](src/algorithms/graph/hamiltonian-cycle) - Visite cada vértice exactamente una vez
* `A` [Problema de las N-Reinas](src/algorithms/uncategorized/n-queens)
* `A` [Gira de Caballeros](src/algorithms/uncategorized/knight-tour)
* `A` [Suma Combinada](src/algorithms/sets/combination-sum) - encuentra todas las combinaciones que forman una suma específica.
* **Ramas y Limites** - recuerde la solución de menor costo encontrada en cada etapa de la búsqueda de rastreo, y utilice el costo de la solución de menor costo encontrada hasta el momento como un límite más bajo en el costo de una solución de menor costo para el problema, a fin de descartar soluciones parciales con costos mayores que la solución de menor costo encontrada hasta el momento. Normalmente se utiliza la travesía BFS en combinación con la travesía DFS del árbol del espacio de estado.
* `A` [Subsecuencia común más larga](src/algorithms/sets/longest-common-subsequence) (LCS)
* `A` [Subcadena común más larga](src/algorithms/string/longest-common-substring)
* `A` [Subsecuencia creciente más larga](src/algorithms/sets/longest-increasing-subsequence)
* `A` [Supersecuencia común más corta](src/algorithms/sets/shortest-common-supersequence)
* `A` [Problema de la mochila 0/1](src/algorithms/sets/knapsack-problem)
* `A` [Partición entera](src/algorithms/math/integer-partition)
* `A` [Máximo subarreglo](src/algorithms/sets/maximum-subarray)
* `A` [Algoritmo de Bellman-Ford](src/algorithms/graph/bellman-ford) - encontrar los caminos más cortos a todos los vértices del grafo desde un solo vértice
* `A` [Algoritmo de Floyd-Warshall](src/algorithms/graph/floyd-warshall) - encontrar los caminos más cortos entre todos los pares de vértices
* `A` [Coincidencia por expresiones regulares](src/algorithms/string/regular-expression-matching)
* **De Retorceso (Backtracking)** - De manera similar a la fuerza bruta, trata de generar todas las soluciones posibles, pero cada vez que genere la siguiente solución, comprueba si cumple con todas las condiciones, y sólo entonces continúa generando soluciones posteriores. De lo contrario, retrocede y sigue un camino diferente para encontrar una solución. Normalmente se utiliza un recorrido en profundidad (DFS) del espacio de estados.
* `P` [Juego de los saltos](src/algorithms/uncategorized/jump-game)
* `P` [Caminos únicos](src/algorithms/uncategorized/unique-paths)
* `P` [Conjunto potencia](src/algorithms/sets/power-set) - todos los subconjuntos de un conjunto
* `A` [Ciclo hamiltoniano](src/algorithms/graph/hamiltonian-cycle) - visitar cada vértice exactamente una vez
* `A` [Problema de las N Reinas](src/algorithms/uncategorized/n-queens)
* `A` [Problema del caballo (Knight tour)](src/algorithms/uncategorized/knight-tour)
* `A` [Suma combinada](src/algorithms/sets/combination-sum) - encuentra todas las combinaciones que forman una suma específica
* **Ramas y Limites** - recuerda la solución de menor costo encontrada en cada etapa de la búsqueda de rastreo, y utilizar el costo de la solución de menor costo encontrada hasta el momento como un límite inferior del costo de una solución de menor costo para el problema, a fin de descartar soluciones parciales con costos mayores que la solución de menor costo encontrada hasta el momento. Normalmente se utiliza un recorrido BFS en combinación con un recorrido DFS del árbol del espacio de estados.
## Como usar este repositorio
## Cómo usar este repositorio
**Instalar las dependencias**
@ -212,7 +226,7 @@ npm test
npm test -- 'LinkedList'
```
**Campo de Juegos**
**Campo de juegos**
Puede jugar con estructuras de datos y algoritmos en el archivo `./src/playground/playground.js` y escribir
pruebas para ello en `./src/playground/__test__/playground.test.js`.
@ -223,19 +237,19 @@ A continuación, simplemente ejecute el siguiente comando para comprobar si el c
npm test -- 'playground'
```
## Información Util
## Información útil
### Refrencias
[▶ Estructuras de datos y Algoritmos en YouTube](https://www.youtube.com/playlist?list=PLLXdhg_r2hKA7DPDsunoDZ-Z769jWn4R8)
[▶ Estructuras de datos y algoritmos en YouTube](https://www.youtube.com/playlist?list=PLLXdhg_r2hKA7DPDsunoDZ-Z769jWn4R8)
### Notación O Grande
Orden de crecimiento de los algoritmos especificados en la notación O grande.
![Graficas de Notación O grande ](./assets/big-o-graph.png)
![Gráficas de Notación O grande ](./assets/big-o-graph.png)
Fuente: [Notación O grande, Hoja de atajos](http://bigocheatsheet.com/).
Fuente: [Big O Cheat Sheet](http://bigocheatsheet.com/).
A continuación se muestra la lista de algunas de las notaciones de Big O más utilizadas y sus comparaciones de rendimiento
frente a diferentes tamaños de los datos de entrada.
@ -250,31 +264,31 @@ frente a diferentes tamaños de los datos de entrada.
| **O(2^N)** | 1024 | 1.26e+29 | 1.07e+301 |
| **O(N!)** | 3628800 | 9.3e+157 | 4.02e+2567 |
### Complejidad de las operaciones de estructura de datos
### Complejidad de las operaciones de estructuras de datos
| Estructura de Datos | Accesso | Busqueda | Inserción | Borrado | Comentarios |
| ------------------------------ | :-----: | :------: | :-------: | :-----: | :-------------------------------------------------------------- |
| **Coleción** | 1 | n | n | n | |
| **Colección** | 1 | n | n | n | |
| **Stack** | n | n | 1 | 1 | |
| **Cola** | n | n | 1 | 1 | |
| **Lista Enlazada** | n | n | 1 | 1 | |
| **Tabla de Hash** | - | n | n | n | En caso de función hash perfecta los costos serían O(1) |
| **Búsqueda por Arbol Binario** | n | n | n | n | En el caso de un árbol equilibrado, los costes serían O(log(n)) |
| **Lista enlazada** | n | n | 1 | 1 | |
| **Tabla hash** | - | n | n | n | En caso de función hash perfecta los costos serían O(1) |
| **Búsqueda por Árbol binario** | n | n | n | n | En el caso de un árbol equilibrado, los costos serían O(log(n)) |
| **Árbol B** | log(n) | log(n) | log(n) | log(n) | |
| **Árbol Rojo-Negro** | log(n) | log(n) | log(n) | log(n) | |
| **Árbol AVL** | log(n) | log(n) | log(n) | log(n) | |
| **Filtro de Bloom** | - | 1 | 1 | - | Falsos positivos son posibles durante la búsqueda |
### Complejidad de Algoritmos de Clasificación de Arreglos
### Complejidad de algoritmos de ordenamiento de arreglos
| Nombre | Mejor | Promedio | Pero | Memorya | Estable | Comentarios |
| -------------------------------- | :-----------: | :---------------------: | :-------------------------: | :-----: | :-----: | :------------------------------------------------------------ |
| **Clasificación de Burbujas** | n | n<sup>2</sup> | n<sup>2</sup> | 1 | Si | |
| **Clasificación por Inserción** | n | n<sup>2</sup> | n<sup>2</sup> | 1 | Si | |
| **Clasificacion por Selección** | n<sup>2</sup> | n<sup>2</sup> | n<sup>2</sup> | 1 | No | |
| **Classificacion por Pila** | n&nbsp;log(n) | n&nbsp;log(n) | n&nbsp;log(n) | 1 | No | |
| **Clasificacion por Fusion** | n&nbsp;log(n) | n&nbsp;log(n) | n&nbsp;log(n) | n | Si | |
| **Quick sort** | n&nbsp;log(n) | n&nbsp;log(n) | n<sup>2</sup> | log(n) | No | Quicksort es utilizqado con O(log(n)) espacio en el stack |
| **Shell sort** | n&nbsp;log(n) | depende de la secuencia de huecos | n&nbsp;(log(n))<sup>2</sup> | 1 | No | |
| **Clasificacion por Conteo** | n + r | n + r | n + r | n + r | Si | r - mayor numero en arreglo |
| **Radix sort** | n \* k | n \* k | n \* k | n + k | Si | k - largo de la llave más larga |
| **Ordenamiento de burbuja** | n | n<sup>2</sup> | n<sup>2</sup> | 1 | Si | |
| **Ordenamiento por inserción** | n | n<sup>2</sup> | n<sup>2</sup> | 1 | Si | |
| **Ordenamiento por selección** | n<sup>2</sup> | n<sup>2</sup> | n<sup>2</sup> | 1 | No | |
| **Ordenamiento por Heap** | n&nbsp;log(n) | n&nbsp;log(n) | n&nbsp;log(n) | 1 | No | |
| **Ordenamiento por mezcla** | n&nbsp;log(n) | n&nbsp;log(n) | n&nbsp;log(n) | n | Si | |
| **Quicksort** | n&nbsp;log(n) | n&nbsp;log(n) | n<sup>2</sup> | log(n) | No | Quicksort utiliza O(log(n)) de espacio en el stack |
| **Shellsort** | n&nbsp;log(n) | depende de la secuencia de huecos | n&nbsp;(log(n))<sup>2</sup> | 1 | No | |
| **Ordenamiento por cuentas** | n + r | n + r | n + r | n + r | Si | r - mayor número en el arreglo |
| **Ordenamiento Radix** | n \* k | n \* k | n \* k | n + k | Si | k - largo de la llave más larga |

View File

@ -15,6 +15,7 @@ _Lisez ceci dans d'autres langues:_
[_简体中文_](README.zh-CN.md),
[_繁體中文_](README.zh-TW.md),
[_한국어_](README.ko-KR.md),
[_日本語_](README.ja-JP.md),
[_Polski_](README.pl-PL.md),
[_Español_](README.es-ES.md),
[_Português_](README.pt-BR.md)

291
README.ja-JP.md Normal file
View File

@ -0,0 +1,291 @@
# JavaScriptアルゴリズムとデータ構造
[![Build Status](https://travis-ci.org/trekhleb/javascript-algorithms.svg?branch=master)](https://travis-ci.org/trekhleb/javascript-algorithms)
[![codecov](https://codecov.io/gh/trekhleb/javascript-algorithms/branch/master/graph/badge.svg)](https://codecov.io/gh/trekhleb/javascript-algorithms)
このリポジトリには、JavaScriptベースの多数のサンプル
一般的なアルゴリズムとデータ構造。
各アルゴリズムとデータ構造には独自のREADMEがあります
関連する説明と、さらに読むためのリンク (関連YouTubeのビデオも含まれてい).
_Read this in other languages:_
[_English_](https://github.com/trekhleb/javascript-algorithms/),
[_简体中文_](README.zh-CN.md),
[_繁體中文_](README.zh-TW.md),
[_한국어_](README.ko-KR.md),
[_Polski_](README.pl-PL.md),
[_Français_](README.fr-FR.md),
[_Español_](README.es-ES.md),
[_Português_](README.pt-BR.md)
## データ構造
データ構造は、データ値、データ値との間の関係、
そして、データを扱うことができる関数と演算の集合で、
データを特定の方法で構成して保存することで、より効率的に
アクセスして変更することができます。
`B` - 初心者, `A` - 上級
* `B` [リンクされたリスト](src/data-structures/linked-list)
* `B` [二重リンクリスト](src/data-structures/doubly-linked-list)
* `B` [キュー](src/data-structures/queue)
* `B` [スタック](src/data-structures/stack)
* `B` [ハッシュ表](src/data-structures/hash-table)
* `B` [ヒープ](src/data-structures/heap) - max and min heap versions
* `B` [優先度キュー](src/data-structures/priority-queue)
* `A` [トライ](src/data-structures/trie)
* `A` [リー](src/data-structures/tree)
* `A` [バイナリ検索ツリー](src/data-structures/tree/binary-search-tree)
* `A` [AVLツリー](src/data-structures/tree/avl-tree)
* `A` [赤黒のリー](src/data-structures/tree/red-black-tree)
* `A` [セグメントツリー](src/data-structures/tree/segment-tree) - with min/max/sum range queries examples
* `A` [フェンウィック・ツリー](src/data-structures/tree/fenwick-tree) (Binary Indexed Tree)
* `A` [グラフ](src/data-structures/graph) (both directed and undirected)
* `A` [分離集合](src/data-structures/disjoint-set)
* `A` [ブルームフィルタ](src/data-structures/bloom-filter)
## アルゴリズム
アルゴリズムとは、問題のクラスをどのように解決するかの明確な仕様です。
一連の操作を正確に定義する一連のルールです。
`B` - 初心者, `A` - 上級
### トピック別アルゴリズム
* **数学**
* `B` [ビット操作](src/algorithms/math/bits) - set/get/update/clear bits, 2つの乗算/除算, 否定的にする. 等
* `B` [因果関係](src/algorithms/math/factorial)
* `B` [フィボナッチ数](src/algorithms/math/fibonacci) - クラシックとクローズドフォームのバージョン
* `B` [素数性テスト](src/algorithms/math/primality-test) (trial division 方法)
* `B` [ユークリッドアルゴリズム](src/algorithms/math/euclidean-algorithm) - 最大公約数を計算する (GCD)
* `B` [最小公倍数](src/algorithms/math/least-common-multiple) (LCM)
* `B` [エラトステネスのふるい](src/algorithms/math/sieve-of-eratosthenes) - 与えられた限度まですべての素数を見つける
* `B` [Is Power of Two](src/algorithms/math/is-power-of-two) - 数値が2の累乗であるかどうかを調べる単純なアルゴリズムとビットごとのアルゴリズム
* `B` [パスカルの三角形](src/algorithms/math/pascal-triangle)
* `B` [複素数](src/algorithms/math/complex-number) - 複素数とその基本演算
* `B` [ラジアン&度](src/algorithms/math/radian) - 度数と逆方向の変換に対するラジアン
* `B` [高速電力供給](src/algorithms/math/fast-powering)
* `A` [整数パーティション](src/algorithms/math/integer-partition)
* `A` [Liu Hui π アルゴリズム](src/algorithms/math/liu-hui) - N-gonsに基づく近似π計算
* `A` [離散フーリエ変換](src/algorithms/math/fourier-transform) - 時間(信号)の関数をそれを構成する周波数に分解する
* **セット**
* `B` [デカルト積 ](src/algorithms/sets/cartesian-product) - 複数の積の積
* `B` [FisherYates Shuffle](src/algorithms/sets/fisher-yates) - 有限シーケンスのランダム置換
* `A` [パワーセット](src/algorithms/sets/power-set) - セットのすべてのサブセット(ビットごとのソリューションとバックトラッキングソリューション)
* `A` [順列](src/algorithms/sets/permutations) (繰り返しの有無にかかわらず)
* `A` [組み合わせ](src/algorithms/sets/combinations) (繰返しあり、繰返しなし)
* `A` [最長共通部分列](src/algorithms/sets/longest-common-subsequence) (LCS)
* `A` [最長増加サブシーケンス](src/algorithms/sets/longest-increasing-subsequence)
* `A` [最短共通スーパーシーケンス](src/algorithms/sets/shortest-common-supersequence) (SCS)
* `A` [ナップザック問題 ](src/algorithms/sets/knapsack-problem) - 「0/1」と「非結合」問題
* `A` [最大サブアレイ](src/algorithms/sets/maximum-subarray) - 「ブルートフォース」と「ダイナミックプログラミング」Kadane's版
* `A` [組み合わせ合計](src/algorithms/sets/combination-sum) - 特定の合計を構成するすべての組み合わせを見つける
* **文字列**
* `B` [ハミング距離](src/algorithms/string/hamming-distance) - シンボルが異なる位置の数
* `A` [レーベンシュタイン距離](src/algorithms/string/levenshtein-distance) - 2つのシーケンス間の最小編集距離
* `A` [Knuth-Morris-Prattアルゴリズム](src/algorithms/string/knuth-morris-pratt) (KMP Algorithm) - 部分文字列検索 (pattern matching)
* `A` [Z アルゴリズム](src/algorithms/string/z-algorithm) - 部分文字列検索 (pattern matching)
* `A` [Rabin Karpアルゴリズム](src/algorithms/string/rabin-karp) - 部分文字列検索
* `A` [最長共通部分文字列](src/algorithms/string/longest-common-substring)
* `A` [正規表現マッチング](src/algorithms/string/regular-expression-matching)
* **検索**
* `B` [リニアサーチ](src/algorithms/search/linear-search)
* `B` [ジャンプ検索](src/algorithms/search/jump-search) (or Block Search) - ソートされた配列で検索
* `B` [バイナリ検索](src/algorithms/search/binary-search) - ソートされた配列で検索
* `B` [補間探索](src/algorithms/search/interpolation-search) - 一様分布のソート配列で検索する
* **並べ替え**
* `B` [バブルソート](src/algorithms/sorting/bubble-sort)
* `B` [選択ソート](src/algorithms/sorting/selection-sort)
* `B` [挿入ソート](src/algorithms/sorting/insertion-sort)
* `B` [ヒープソート](src/algorithms/sorting/heap-sort)
* `B` [マージソート](src/algorithms/sorting/merge-sort)
* `B` [クイックソート](src/algorithms/sorting/quick-sort) -インプレースおよび非インプレース・インプリメンテーション
* `B` [シェルソート](src/algorithms/sorting/shell-sort)
* `B` [並べ替えを数える](src/algorithms/sorting/counting-sort)
* `B` [基数ソート](src/algorithms/sorting/radix-sort)
* **リンクされたリスト**
* `B` [ストレートトラバーサル](src/algorithms/linked-list/traversal)
* `B` [逆方向のトラバーサル](src/algorithms/linked-list/reverse-traversal)
* **ツリー**
* `B` [深度優先検索](src/algorithms/tree/depth-first-search) (DFS)
* `B` [幅優先検索](src/algorithms/tree/breadth-first-search) (BFS)
* **グラフ**
* `B` [深度優先検索](src/algorithms/graph/depth-first-search) (DFS)
* `B` [幅優先検索](src/algorithms/graph/breadth-first-search) (BFS)
* `B` [Kruskalのアルゴリズム](src/algorithms/graph/kruskal) - 重み付き無向グラフの最小スパニングツリーMSTの発見
* `A` [Dijkstraアルゴリズム](src/algorithms/graph/dijkstra) - 単一の頂点からすべてのグラフ頂点への最短経路を見つける
* `A` [Bellman-Fordアルゴリズム](src/algorithms/graph/bellman-ford) - 単一の頂点からすべてのグラフ頂点への最短経路を見つける
* `A` [Floyd-Warshallアルゴリズム](src/algorithms/graph/floyd-warshall) - すべての頂点ペア間の最短経路を見つける
* `A` [Detect Cycle](src/algorithms/graph/detect-cycle) - 有向グラフと無向グラフの両方DFSおよびディスジョイントセットベースのバージョン
* `A` [プリムのアルゴリズム](src/algorithms/graph/prim) - 重み付き無向グラフの最小スパニングツリーMSTの発見
* `A` [トポロジカルソート](src/algorithms/graph/topological-sorting) - DFSメソッド
* `A` [アーティキュレーションポイント](src/algorithms/graph/articulation-points) - TarjanのアルゴリズムDFSベース
* `A` [ブリッジ ](src/algorithms/graph/bridges) - DFSベースのアルゴリズム
* `A` [オイラーパスとオイラー回路](src/algorithms/graph/eulerian-path) - フルリーアルゴリズム - すべてのエッジを正確に1回訪問する
* `A` [ハミルトニアンサイクル](src/algorithms/graph/hamiltonian-cycle) - すべての頂点を正確に1回訪問する
* `A` [強連結成分](src/algorithms/graph/strongly-connected-components) - コサラジュのアルゴリズム
* `A` [トラベリングセールスマン問題](src/algorithms/graph/travelling-salesman) - 各都市を訪問し、起点都市に戻る最短経路
* **暗号**
* `B` [多項式ハッシュ](src/algorithms/cryptography/polynomial-hash) - 関数多項式に基づくハッシュ関数
* **未分類**
* `B` [ハノイの塔](src/algorithms/uncategorized/hanoi-tower)
* `B` [正方行列回転](src/algorithms/uncategorized/square-matrix-rotation) - インプレイスアルゴリズム
* `B` [ジャンプゲーム](src/algorithms/uncategorized/jump-game) - バックトラック、ダイナミックプログラミング(トップダウン+ボトムアップ)、欲張りの例
* `B` [ユニークなパス](src/algorithms/uncategorized/unique-paths) - バックトラック、動的プログラミング、PascalのTriangleベースの例
* `B` [レインテラス](src/algorithms/uncategorized/rain-terraces) - トラップ雨水問題(ダイナミックプログラミングとブルートフォースバージョン)
* `B` [再帰的階段](src/algorithms/uncategorized/recursive-staircase) - 上に到達する方法の数を数える4つのソリューション
* `A` [N-クイーンズ問題](src/algorithms/uncategorized/n-queens)
* `A` [ナイトツアー](src/algorithms/uncategorized/knight-tour)
### Paradigmによるアルゴリズム
アルゴリズムパラダイムは、あるクラスのアルゴリズムの設計の基礎をなす一般的な方法またはアプローチである。それは、アルゴリズムがコンピュータプログラムよりも高い抽象であるのと同様に、アルゴリズムの概念よりも高い抽象である。
* **ブルートフォース** - べての可能性を見て最適なソリューションを選択する
* `B` [線形探索](src/algorithms/search/linear-search)
* `B` [レインテラス](src/algorithms/uncategorized/rain-terraces) - 雨水問題
* `B` [Recursive Staircase](src/algorithms/uncategorized/recursive-staircase) - 先頭に到達する方法の数を数えます
* `A` [最大サブアレイ](src/algorithms/sets/maximum-subarray)
* `A` [旅行セールスマン問題](src/algorithms/graph/travelling-salesman) - 各都市を訪れ、起点都市に戻る最短ルート
* `A` [離散フーリエ変換](src/algorithms/math/fourier-transform) - 時間(信号)の関数をそれを構成する周波数に分解する
* **欲張り** - 未来を考慮することなく、現時点で最適なオプションを選択する
* `B` [ジャンプゲーム](src/algorithms/uncategorized/jump-game)
* `A` [結合されていないナップザック問題](src/algorithms/sets/knapsack-problem)
* `A` [Dijkstra Algorithm](src/algorithms/graph/dijkstra) - すべてのグラフ頂点への最短経路を見つける
* `A` [Prims Algorithm](src/algorithms/graph/prim) - 重み付き無向グラフの最小スパニングツリーMSTを見つける
* `A` [Kruskalのアルゴリズム](src/algorithms/graph/kruskal) - 重み付き無向グラフの最小スパニングツリーMSTを見つける
* **分割と征服** - 問題をより小さな部分に分割し、それらの部分を解決する
* `B` [バイナリ検索](src/algorithms/search/binary-search)
* `B` [ハノイの塔](src/algorithms/uncategorized/hanoi-tower)
* `B` [パスカルの三角形](src/algorithms/math/pascal-triangle)
* `B` [ユークリッドアルゴリズム](src/algorithms/math/euclidean-algorithm) - GCDGreatest Common Divisorを計算する
* `B` [マージソート](src/algorithms/sorting/merge-sort)
* `B` [クイックソート](src/algorithms/sorting/quick-sort)
* `B` [ツリーの深さ優先検索](src/algorithms/tree/depth-first-search) (DFS)
* `B` [グラフの深さ優先検索](src/algorithms/graph/depth-first-search) (DFS)
* `B` [ジャンプゲーム](src/algorithms/uncategorized/jump-game)
* `B` [高速電力供給](src/algorithms/math/fast-powering)
* `A` [順列](src/algorithms/sets/permutations) (繰り返しの有無にかかわらず)
* `A` [組み合わせ](src/algorithms/sets/combinations)(繰返しあり、繰返しなし)
* **動的プログラミング** - 以前に発見されたサブソリューションを使用してソリューションを構築する
* `B` [フィボナッチ数](src/algorithms/math/fibonacci)
* `B` [ジャンプゲーム](src/algorithms/uncategorized/jump-game)
* `B` [ユニークなパス](src/algorithms/uncategorized/unique-paths)
* `B` [雨テラス](src/algorithms/uncategorized/rain-terraces) - トラップ雨水問題
* `B` [再帰的階段](src/algorithms/uncategorized/recursive-staircase) - 上に到達する方法の数を数える
* `A` [Levenshtein Distance](src/algorithms/string/levenshtein-distance) - 2つのシーケンス間の最小編集距離
* `A` [最長共通部分列](src/algorithms/sets/longest-common-subsequence) (LCS)
* `A` [最長共通部分文字列](src/algorithms/string/longest-common-substring)
* `A` [最長増加サブシーケンス](src/algorithms/sets/longest-increasing-subsequence)
* `A` [最短共通共通配列](src/algorithms/sets/shortest-common-supersequence)
* `A` [0/1ナップザック問題](src/algorithms/sets/knapsack-problem)
* `A` [整数パーティション](src/algorithms/math/integer-partition)
* `A` [最大サブアレイ](src/algorithms/sets/maximum-subarray)
* `A` [Bellman-Fordアルゴリズム](src/algorithms/graph/bellman-ford) - すべてのグラフ頂点への最短経路を見つける
* `A` [Floyd-Warshallアルゴリズム](src/algorithms/graph/floyd-warshall) - すべての頂点ペア間の最短経路を見つける
* `A` [正規表現マッチング](src/algorithms/string/regular-expression-matching)
* **バックトラッキング** - ブルートフォースと同様に、可能なすべてのソリューションを生成しようとしますが、
次のソリューションを生成するたびにすべての条件を満たすかどうかをテストし、それ以降は引き続きソリューションを生成します。
それ以外の場合は、バックトラックして、解決策を見つける別の経路に進みます。
通常、状態空間のDFSトラバーサルが使用されています。
* `B` [ジャンプゲーム](src/algorithms/uncategorized/jump-game)
* `B` [ユニークなパス](src/algorithms/uncategorized/unique-paths)
* `B` [パワーセット](src/algorithms/sets/power-set) - セットのすべてのサブセット
* `A` [ハミルトニアンサイクル](src/algorithms/graph/hamiltonian-cycle) - すべての頂点を正確に1回訪問する
* `A` [N-クイーンズ問題](src/algorithms/uncategorized/n-queens)
* `A` [ナイトツアー](src/algorithms/uncategorized/knight-tour)
* `A` [組み合わせ合計](src/algorithms/sets/combination-sum) - 特定の合計を構成するすべての組み合わせを見つける
* **ブランチ&バウンド** - バックトラック検索の各段階で見つかった最もコストの低いソリューションを覚えておいて、最もコストの低いソリューションのコストを使用します。これまでに発見された最もコストの低いソリューションよりも大きなコストで部分ソリューションを破棄するように指示します。通常、状態空間ツリーのDFSトラバーサルと組み合わせたBFSトラバーサルが使用されています。
## このリポジトリの使い方
**すべての依存関係をインストールする**
```
npm install
```
**ESLintを実行する**
これを実行してコードの品質をチェックすることができます。
```
npm run lint
```
**すべてのテストを実行する**
```
npm test
```
**名前でテストを実行する**
```
npm test -- 'LinkedList'
```
**playground**
データ構造とアルゴリズムを `./src/playground/playground.js` ファイルで再生し、
それに対するテストを書くことができ `./src/playground/__test__/playground.test.js`.
次に、次のコマンドを実行して、遊び場コードが正常に動作するかどうかをテストします。
```
npm test -- 'playground'
```
## 有用な情報
### 参考文献
[▶ データ構造とアルゴリズム on YouTube](https://www.youtube.com/playlist?list=PLLXdhg_r2hKA7DPDsunoDZ-Z769jWn4R8)
### ビッグO表記
*Big O表記法は* 入力サイズが大きくなるにつれて実行時間やスペース要件がどのように増加するかに応じてアルゴリズムを分類するために使用されます。下のチャートでは、Big O表記で指定されたアルゴリズムの成長の最も一般的な順序を見つけることができます。
![Big Oグラフ](./assets/big-o-graph.png)
出典: [Big Oチートシート](http://bigocheatsheet.com/).
以下は、最も使用されているBig O表記のリストと、入力データのさまざまなサイズに対するパフォーマンス比較です。
| Big O Notation | Computations for 10 elements | Computations for 100 elements | Computations for 1000 elements |
| -------------- | ---------------------------- | ----------------------------- | ------------------------------- |
| **O(1)** | 1 | 1 | 1 |
| **O(log N)** | 3 | 6 | 9 |
| **O(N)** | 10 | 100 | 1000 |
| **O(N log N)** | 30 | 600 | 9000 |
| **O(N^2)** | 100 | 10000 | 1000000 |
| **O(2^N)** | 1024 | 1.26e+29 | 1.07e+301 |
| **O(N!)** | 3628800 | 9.3e+157 | 4.02e+2567 |
### データ構造操作の複雑さ
| Data Structure | Access | Search | Insertion | Deletion | Comments |
| ----------------------- | :-------: | :-------: | :-------: | :-------: | :-------- |
| **Array** | 1 | n | n | n | |
| **Stack** | n | n | 1 | 1 | |
| **Queue** | n | n | 1 | 1 | |
| **Linked List** | n | n | 1 | 1 | |
| **Hash Table** | - | n | n | n | In case of perfect hash function costs would be O(1) |
| **Binary Search Tree** | n | n | n | n | In case of balanced tree costs would be O(log(n)) |
| **B-Tree** | log(n) | log(n) | log(n) | log(n) | |
| **Red-Black Tree** | log(n) | log(n) | log(n) | log(n) | |
| **AVL Tree** | log(n) | log(n) | log(n) | log(n) | |
| **Bloom Filter** | - | 1 | 1 | - | False positives are possible while searching |
### 配列の並べ替えアルゴリズムの複雑さ
| Name | Best | Average | Worst | Memory | Stable | Comments |
| --------------------- | :-------------: | :-----------------: | :-----------------: | :-------: | :-------: | :-------- |
| **Bubble sort** | n | n<sup>2</sup> | n<sup>2</sup> | 1 | Yes | |
| **Insertion sort** | n | n<sup>2</sup> | n<sup>2</sup> | 1 | Yes | |
| **Selection sort** | n<sup>2</sup> | n<sup>2</sup> | n<sup>2</sup> | 1 | No | |
| **Heap sort** | n&nbsp;log(n) | n&nbsp;log(n) | n&nbsp;log(n) | 1 | No | |
| **Merge sort** | n&nbsp;log(n) | n&nbsp;log(n) | n&nbsp;log(n) | n | Yes | |
| **Quick sort** | n&nbsp;log(n) | n&nbsp;log(n) | n<sup>2</sup> | log(n) | No | Quicksort is usually done in-place with O(log(n)) stack space |
| **Shell sort** | n&nbsp;log(n) | depends on gap sequence | n&nbsp;(log(n))<sup>2</sup> | 1 | No | |
| **Counting sort** | n + r | n + r | n + r | n + r | Yes | r - biggest number in array |
| **Radix sort** | n * k | n * k | n * k | n + k | Yes | k - length of longest key |

View File

@ -12,6 +12,7 @@ _Read this in other languages:_
[_English_](https://github.com/trekhleb/javascript-algorithms/),
[_简体中文_](README.zh-CN.md),
[_繁體中文_](README.zh-TW.md),
[_日本語_](README.ja-JP.md),
[_Polski_](README.pl-PL.md),
[_Français_](README.fr-FR.md),
[_Español_](README.es-ES.md),
@ -130,9 +131,7 @@ _Read this in other languages:_
### 패러다임별 알고리즘
알고리즘의 패러다임은 어떤 종류의 알고리즘을 설계할 때 기초가 되는 일반적인 방법 혹은 접근법입니다.
알고리즘이 컴퓨터의 프로그램 보다 더 추상적인 것처럼 알고리즘의 패러다임은 어떤 알고리즘의
개념보다 추상적인 것입니다.
알고리즘 패러다임 이란, 알고리즘이 주어진 문제를 해결하기 위해 채택한 기초가 되는 일반적인 방법 혹은 접근법입니다. 알고리즘이 해결하는 문제나 알고리즘의 동작 방식이 완전히 다르더라도,알고리즘의 동작 원칙이 같으면 같은 패러다음을 사용했다고 말할 수 있으며, 주로 알고리즘을 구분하는 기준으로 쓰인다. 알고리즘이 일반적인 컴퓨터의 프로그램에 대한 개념보다 보다 더 추상적인 개념인 것처럼 알고리즘의 패러다임은 명확히 정의된 수학적 실체가 있는 것이 아니기 때문에 그 어떤 알고리즘의 개념보다도 훨씬 추상적인 개념이다.
* **브루트 포스(Brute Force)** - 가능한 모든 경우를 탐색한 뒤 최적을 찾아내는 방식입니다.
* `B` [선형 탐색](src/algorithms/search/linear-search)
@ -180,11 +179,11 @@ _Read this in other languages:_
* `A` [N-Queens 문제](src/algorithms/uncategorized/n-queens)
* `A` [기사의 여행](src/algorithms/uncategorized/knight-tour)
* `A` [조합 합](src/algorithms/sets/combination-sum) - 특정 합을 구성하는 모든 조합 찾기
* **분기 한정법** - 백트래킹으로 찾은 각 단계의 최소 비용 해결법을 기억해 두고 있다가, 이 비용을 이용해서 더 낮은 최소 비용을 찾습니다. 기억해둔 최소 비용을 이용해 더 높은 비용이 드는 해결법은 더이상 탐색하지 않습니다. 보통 상태 정보를 사진 DFS 를 이용한 BFS 방식에서 사용됩니다.
* **분기 한정법** - 백트래킹으로 찾은 각 단계의 최소 비용이 드는 해를 기억해 두고 있다가, 이 비용을 이용해서 더 낮은 최적의 해를 찾습니다. 기억해둔 최소 비용들을 이용해 더 높은 비용이 드는 해결법을 탐색 안함으로써 불필요한 시간 소모를 줄입니다. 보통 상태 공간 트리의 DFS 탐색을 이용한 BFS 탐색 방식에서 사용됩니다.
## 이 저장소의 사용법
**모든 의존성 설치**
**모든 종속 모듈들 설치**
```
npm install
```

View File

@ -14,6 +14,7 @@ _Read this in other languages:_
[_简体中文_](README.zh-CN.md),
[_繁體中文_](README.zh-TW.md),
[_한국어_](README.ko-KR.md),
[_日本語_](README.ja-JP.md),
[_Polski_](README.pl-PL.md),
[_Français_](README.fr-FR.md),
[_Español_](README.es-ES.md),
@ -139,6 +140,7 @@ a set of rules that precisely define a sequence of operations.
* `B` [Jump Game](src/algorithms/uncategorized/jump-game) - backtracking, dynamic programming (top-down + bottom-up) and greedy examples
* `B` [Unique Paths](src/algorithms/uncategorized/unique-paths) - backtracking, dynamic programming and Pascal's Triangle based examples
* `B` [Rain Terraces](src/algorithms/uncategorized/rain-terraces) - trapping rain water problem (dynamic programming and brute force versions)
* `B` [Recursive Staircase](src/algorithms/uncategorized/recursive-staircase) - count the number of ways to reach to the top (4 solutions)
* `A` [N-Queens Problem](src/algorithms/uncategorized/n-queens)
* `A` [Knight's Tour](src/algorithms/uncategorized/knight-tour)
@ -151,6 +153,7 @@ algorithm is an abstraction higher than a computer program.
* **Brute Force** - look at all the possibilities and selects the best solution
* `B` [Linear Search](src/algorithms/search/linear-search)
* `B` [Rain Terraces](src/algorithms/uncategorized/rain-terraces) - trapping rain water problem
* `B` [Recursive Staircase](src/algorithms/uncategorized/recursive-staircase) - count the number of ways to reach to the top
* `A` [Maximum Subarray](src/algorithms/sets/maximum-subarray)
* `A` [Travelling Salesman Problem](src/algorithms/graph/travelling-salesman) - shortest possible route that visits each city and returns to the origin city
* `A` [Discrete Fourier Transform](src/algorithms/math/fourier-transform) - decompose a function of time (a signal) into the frequencies that make it up
@ -178,6 +181,7 @@ algorithm is an abstraction higher than a computer program.
* `B` [Jump Game](src/algorithms/uncategorized/jump-game)
* `B` [Unique Paths](src/algorithms/uncategorized/unique-paths)
* `B` [Rain Terraces](src/algorithms/uncategorized/rain-terraces) - trapping rain water problem
* `B` [Recursive Staircase](src/algorithms/uncategorized/recursive-staircase) - count the number of ways to reach to the top
* `A` [Levenshtein Distance](src/algorithms/string/levenshtein-distance) - minimum edit distance between two sequences
* `A` [Longest Common Subsequence](src/algorithms/sets/longest-common-subsequence) (LCS)
* `A` [Longest Common Substring](src/algorithms/string/longest-common-substring)

View File

@ -15,6 +15,7 @@ _Read this in other languages:_
[_简体中文_](README.zh-CN.md),
[_繁體中文_](README.zh-TW.md),
[_한국어_](README.ko-KR.md),
[_日本語_](README.ja-JP.md),
[_Français_](README.fr-FR.md),
[_Español_](README.es-ES.md),
[_Português_](README.pt-BR.md)

View File

@ -15,6 +15,7 @@ _Leia isto em outros idiomas:_
[_简体中文_](README.zh-CN.md),
[_繁體中文_](README.zh-TW.md),
[_한국어_](README.ko-KR.md),
[_日本語_](README.ja-JP.md),
[_Polski_](README.pl-PL.md),
[_Français_](README.fr-FR.md),
[_Español_](README.es-ES.md)

View File

@ -5,36 +5,39 @@
本仓库包含了多种基于 JavaScript 的算法与数据结构。
每种算法和数据结构都有自己的 README 并提供相关说明以及进一步阅读和 YouTube 视频
每种算法和数据结构都有自己的 README,包含相关说明和链接,以便进一步阅读 (还有 YouTube 视频)
_Read this in other languages:_
[_English_](https://github.com/trekhleb/javascript-algorithms/),
[_繁體中文_](README.zh-TW.md),
[_한국어_](README.ko-KR.md),
[_日本語_](README.ja-JP.md),
[_Polski_](README.pl-PL.md),
[_Français_](README.fr-FR.md),
[_Español_](README.es-ES.md),
[_Português_](README.pt-BR.md)
*注意:这个项目仅用于学习和研究,**不是**用于生产环境。*
## 数据结构
数据结构是在计算机中 组织和存储数 据的一种特殊方式, 它可以高效地 访问和修改 数据。更确切地说, 数据结构是数据值的集合, 它们之间的关系、函数或操作可以应用于数据
数据结构是在计算机中组织和存储数据的一种特殊方式,使得数据可以高效地被访问和修改。更确切地说,数据结构是数据值的集合,表示数据之间的关系,也包括了作用在数据上的函数或操作
`B` - 初学者, `A` - 进阶
`B` - 初学者 `A` - 进阶
* `B` [链表](src/data-structures/linked-list/README.zh-CN.md)
* `B` [双向链表](src/data-structures/doubly-linked-list/README.zh-CN.md)
* `B` [队列](src/data-structures/queue/README.zh-CN.md)
* `B` [](src/data-structures/stack/README.zh-CN.md)
* `B` [哈希表](src/data-structures/hash-table/README.zh-CN.md)
* `B` [](src/data-structures/heap/README.zh-CN.md)
* `B` [](src/data-structures/heap/README.zh-CN.md) - 最大堆 & 最小堆
* `B` [优先队列](src/data-structures/priority-queue/README.zh-CN.md)
* `A` [字典树](src/data-structures/trie)
* `A` [字典树](src/data-structures/trie/README.zh-CN.md)
* `A` [](src/data-structures/tree/README.zh-CN.md)
* `A` [二叉查找树](src/data-structures/tree/binary-search-tree)
* `A` [AVL 树](src/data-structures/tree/avl-tree)
* `A` [红黑树](src/data-structures/tree/red-black-tree)
* `A` [线段树](src/data-structures/tree/segment-tree) - 使用 最小/最大/总和 范围查询示例
* `A` [线段树](src/data-structures/tree/segment-tree) - 使用 `最小/最大/总和` 范围查询示例
* `A` [树状数组](src/data-structures/tree/fenwick-tree) (二叉索引树)
* `A` [](src/data-structures/graph/README.zh-CN.md) (有向图与无向图)
* `A` [并查集](src/data-structures/disjoint-set)
@ -42,118 +45,133 @@ _Read this in other languages:_
## 算法
算法是如何解决一类问题的明确规范。 算法是一组精确定义操作序列的规则。
算法是如何解决一类问题的明确规范。算法是一组精确定义操作序列的规则。
`B` - 初学者, `A` - 进阶
### 算法主题
* **数学**
* `B` [Bit 操控](src/algorithms/math/bits) - set/get/update/clear 位, 乘以/除以 二进制位, 变负 等.
* `B` [阶乘](src/algorithms/math/factorial)
* `B` [斐波那契数](src/algorithms/math/fibonacci)
* **数学**
* `B` [Bit 操控](src/algorithms/math/bits) - set/get/update/clear 位、乘以/除以二进制位 、变负等
* `B` [阶乘](src/algorithms/math/factorial/README.zh-CN.md)
* `B` [斐波那契数](src/algorithms/math/fibonacci) - `经典``闭式` 版本
* `B` [素数检测](src/algorithms/math/primality-test) (排除法)
* `B` [欧几里得算法](src/algorithms/math/euclidean-algorithm) - 计算最大公约数 (GCD)
* `B` [最小公倍数](src/algorithms/math/least-common-multiple) (LCM)
* `B` [素数筛](src/algorithms/math/sieve-of-eratosthenes) - 查找所有素数达到任何给定限制
* `B` [判断2次方数](src/algorithms/math/is-power-of-two) - 检查数字是否为2的幂 (原生和按位算法)
* `B` [素数筛](src/algorithms/math/sieve-of-eratosthenes) - 查找任意给定范围内的所有素数
* `B` [判断 2 次方数](src/algorithms/math/is-power-of-two) - 检查数字是否为 2 的幂 (原生和按位算法)
* `B` [杨辉三角形](src/algorithms/math/pascal-triangle)
* `B` [复数](src/algorithms/math/complex-number) - 复数及其基本运算
* `B` [弧度和角](src/algorithms/math/radian) - 弧度与角的相互转换
* `B` [快速算次方](src/algorithms/math/fast-powering)
* `A` [整数拆分](src/algorithms/math/integer-partition)
* `A` [割圆术](src/algorithms/math/liu-hui) - 基于N-gons的近似π计算
* `A` [割圆术](src/algorithms/math/liu-hui) - 基于 N-gons 的近似 π 计算
* `A` [离散傅里叶变换](src/algorithms/math/fourier-transform) - 把时间信号解析成构成它的频率
* **集合**
* `B` [笛卡尔积](src/algorithms/sets/cartesian-product) - 多集合结果
* `A` [洗牌算法](src/algorithms/sets/fisher-yates) - 随机置换有限序列
* `A` [幂集](src/algorithms/sets/power-set) - 该集合的所有子集
* `A` [排列](src/algorithms/sets/permutations) (有/无重复)
* `A` [组合](src/algorithms/sets/combinations) (有/无重复)
* `A` [洗牌算法](src/algorithms/sets/fisher-yates) - 随机置换有限序列
* `A` [最长公共子序列](src/algorithms/sets/longest-common-subsequence) (LCS)
* `A` [最长递增子序列](src/algorithms/sets/longest-increasing-subsequence)
* `A` [最短公共父序列](src/algorithms/sets/shortest-common-supersequence) (SCS)
* `A` [背包问题](src/algorithms/sets/knapsack-problem) - "0/1" and "Unbound" ones
* `A` [最大子数列问题](src/algorithms/sets/maximum-subarray) - BF算法 与 动态规划
* `A` [背包问题](src/algorithms/sets/knapsack-problem) - `0/1``无边界` 问题
* `A` [最大子数列问题](src/algorithms/sets/maximum-subarray) - `BF 算法``动态规划`
* `A` [组合求和](src/algorithms/sets/combination-sum) - 查找形成特定总和的所有组合
* **字符串**
* `A` [莱温斯坦距离](src/algorithms/string/levenshtein-distance) - 两个序列之间的最小编辑距离
* `B` [汉明距离](src/algorithms/string/hamming-distance) - 符号不同的位置数
* `A` [KMP算法](src/algorithms/string/knuth-morris-pratt) (克努斯-莫里斯-普拉特算法) - 子串搜索 (模式匹配)
* `A` [字符串快速查找](src/algorithms/string/rabin-karp) - 子串搜索
* `A` [莱温斯坦距离](src/algorithms/string/levenshtein-distance) - 两个序列之间的最小编辑距离
* `A` [KnuthMorrisPratt 算法](src/algorithms/string/knuth-morris-pratt) KMP 算法 - 子串搜索 (模式匹配)
* `A` [字符串快速查找](src/algorithms/string/rabin-karp) - 子串搜索 (模式匹配)
* `A` [Rabin Karp 算法](src/algorithms/string/rabin-karp) - 子串搜索
* `A` [最长公共子串](src/algorithms/string/longest-common-substring)
* `A` [正则表达式匹配](src/algorithms/string/regular-expression-matching)
* `A` [正则表达式匹配](src/algorithms/string/regular-expression-matching)
* **搜索**
* `B` [线性搜索](src/algorithms/search/linear-search)
* `B` [跳转搜索](src/algorithms/search/jump-search) (或块搜索) - 搜索排序数组
* `B` [二分查找](src/algorithms/search/binary-search)
* `B` [插值搜索](src/algorithms/search/interpolation-search) - 搜索均匀分布的序数组
* `B` [跳转搜索/块搜索](src/algorithms/search/jump-search) - 搜索有序数组
* `B` [二分查找](src/algorithms/search/binary-search) - 搜索有序数组
* `B` [插值搜索](src/algorithms/search/interpolation-search) - 搜索均匀分布的序数组
* **排序**
* `B` [冒泡排序](src/algorithms/sorting/bubble-sort)
* `B` [选择排序](src/algorithms/sorting/selection-sort)
* `B` [插入排序](src/algorithms/sorting/insertion-sort)
* `B` [堆排序](src/algorithms/sorting/heap-sort)
* `B` [归并排序](src/algorithms/sorting/merge-sort)
* `B` [快速排序](src/algorithms/sorting/quick-sort)
* `B` [快速排序](src/algorithms/sorting/quick-sort) - in-place (原地) 和 non-in-place 版本
* `B` [希尔排序](src/algorithms/sorting/shell-sort)
* `B` [计数排序](src/algorithms/sorting/counting-sort)
* `B` [基数排序](src/algorithms/sorting/radix-sort)
* **链表**
- `B` [正向遍历](src/algorithms/linked-list/traversal)
- `B` [反向遍历](src/algorithms/linked-list/reverse-traversal)
* **树**
* `B` [深度优先搜索](src/algorithms/tree/depth-first-search) (DFS)
* `B` [广度优先搜索](src/algorithms/tree/breadth-first-search) (BFS)
* **图**
* `B` [深度优先搜索](src/algorithms/graph/depth-first-search) (DFS)
* `B` [广度优先搜索](src/algorithms/graph/breadth-first-search) (BFS)
* `B` [克鲁斯克尔演算法](src/algorithms/graph/kruskal) - 寻找加权无向图的最小生成树 (MST)
* `A` [戴克斯特拉算法](src/algorithms/graph/dijkstra) - 找到图中所有顶点的最短路径
* `A` [贝尔曼-福特算法](src/algorithms/graph/bellman-ford) - 找到图中所有顶点的最短路径
* `A` [弗洛伊德算法](src/algorithms/graph/floyd-warshall) - 找到所有顶点对 之间的最短路径
* `A` [判圈算法](src/algorithms/graph/detect-cycle) - 对于有向图和无向图 (基于DFS和不相交集的版本)
* `A` [判圈算法](src/algorithms/graph/detect-cycle) - 对于有向图和无向图 (基于 DFS 和不相交集的版本)
* `A` [普林演算法](src/algorithms/graph/prim) - 寻找加权无向图的最小生成树 (MST)
* `B` [克鲁斯克尔演算法](src/algorithms/graph/kruskal) - 寻找加权无向图的最小生成树 (MST)
* `A` [拓扑排序](src/algorithms/graph/topological-sorting) - DFS 方法
* `A` [关节点](src/algorithms/graph/articulation-points) - Tarjan算法 (基于DFS)
* `A` [](src/algorithms/graph/bridges) - 基于DFS的算法
* `A` [欧拉回径与一笔画问题](src/algorithms/graph/eulerian-path) - Fleury的算法 - 一次访问每个边
* `A` [关节点](src/algorithms/graph/articulation-points) - Tarjan 算法 (基于 DFS)
* `A` [](src/algorithms/graph/bridges) - 基于 DFS 的算法
* `A` [欧拉回径与一笔画问题](src/algorithms/graph/eulerian-path) - Fleury 的算法 - 一次访问每个边
* `A` [哈密顿图](src/algorithms/graph/hamiltonian-cycle) - 恰好访问每个顶点一次
* `A` [强连通分量](src/algorithms/graph/strongly-connected-components) - Kosaraju算法
* `A` [强连通分量](src/algorithms/graph/strongly-connected-components) - Kosaraju 算法
* `A` [旅行推销员问题](src/algorithms/graph/travelling-salesman) - 尽可能以最短的路线访问每个城市并返回原始城市
* **加密**
* `B` [多项式 hash](src/algorithms/cryptography/polynomial-hash) - 基于多项式的 rolling hash 函数
* **未分类**
* `B` [汉诺塔](src/algorithms/uncategorized/hanoi-tower)
* `B` [旋转矩阵](src/algorithms/uncategorized/square-matrix-rotation) - 原地算法
* `B` [跳跃 游戏](src/algorithms/uncategorized/jump-game) - 回溯, 动态编程 (自上而下+自下而上) 和贪婪的例子
* `B` [独特(唯一) 路径](src/algorithms/uncategorized/unique-paths) - 回溯, 动态编程和基于Pascal三角形的例子
* `B` [跳跃游戏](src/algorithms/uncategorized/jump-game) - 回溯,动态编程 (自上而下+自下而上) 和贪婪的例子
* `B` [独特(唯一) 路径](src/algorithms/uncategorized/unique-paths) - 回溯、动态编程和基于 Pascal 三角形的例子
* `B` [雨水收集](src/algorithms/uncategorized/rain-terraces) - 诱捕雨水问题 (动态编程和暴力版本)
* `B` [递归楼梯](src/algorithms/uncategorized/recursive-staircase) - 计算有共有多少种方法可以到达顶层 (4 种解题方案)
* `A` [八皇后问题](src/algorithms/uncategorized/n-queens)
* `A` [骑士巡逻](src/algorithms/uncategorized/knight-tour)
### 算法范式
算法范式是基于类的设计的通用方法或方法的算法。 这是一个比算法概念更高的抽象, 就像一个
算法是比计算机程序更高的抽象。
算法范式是一种通用方法,基于一类算法的设计。这是比算法更高的抽象,就像算法是比计算机程序更高的抽象。
* **BF算法** - 查找/搜索 所有可能性并选择最佳解决方案
* **BF 算法** - `查找/搜索` 所有可能性并选择最佳解决方案
* `B` [线性搜索](src/algorithms/search/linear-search)
* `B` [雨水收集](src/algorithms/uncategorized/rain-terraces) - 诱导雨水问题
* `B` [递归楼梯](src/algorithms/uncategorized/recursive-staircase) - 计算有共有多少种方法可以到达顶层 (4 种解题方案)
* `A` [最大子数列](src/algorithms/sets/maximum-subarray)
* `A` [旅行推销员问题](src/algorithms/graph/travelling-salesman) - 尽可能以最短的路线访问每个城市并返回原始城市
* **贪心法** - 在当前选择最佳选项, 不考虑以后情况
* `A` [离散傅里叶变换](src/algorithms/math/fourier-transform) - 把时间信号解析成构成它的频率
* **贪心法** - 在当前选择最佳选项不考虑以后情况
* `B` [跳跃游戏](src/algorithms/uncategorized/jump-game)
* `A` [背包问题](src/algorithms/sets/knapsack-problem)
* `A` [戴克斯特拉算法](src/algorithms/graph/dijkstra) - 找到所有图顶点的最短路径
* `A` [普里姆算法](src/algorithms/graph/prim) - 寻找加权无向图的最小生成树 (MST)
* `A` [克鲁斯卡尔算法](src/algorithms/graph/kruskal) - 寻找加权无向图的最小生成树 (MST)
* **分治法** - 将问题分成较小的部分, 然后解决这些部分
* **分治法** - 将问题分成较小的部分然后解决这些部分
* `B` [二分查找](src/algorithms/search/binary-search)
* `B` [汉诺塔](src/algorithms/uncategorized/hanoi-tower)
* `B` [杨辉三角形](src/algorithms/math/pascal-triangle)
* `B` [欧几里得算法](src/algorithms/math/euclidean-algorithm) - 计算最大公约数 (GCD)
* `B` [跳跃游戏](src/algorithms/uncategorized/jump-game)
* `B` [归并排序](src/algorithms/sorting/merge-sort)
* `B` [快速排序](src/algorithms/sorting/quick-sort)
* `B` [树深度优先搜索](src/algorithms/tree/depth-first-search) (DFS)
* `B` [图深度优先搜索](src/algorithms/graph/depth-first-search) (DFS)
* `B` [跳跃游戏](src/algorithms/uncategorized/jump-game)
* `B` [快速算次方](src/algorithms/math/fast-powering)
* `A` [排列](src/algorithms/sets/permutations) (有/无重复)
* `A` [组合](src/algorithms/sets/combinations) (有/无重复)
* **动态编程** - 使用以前找到的子解决方案构建解决方案
* **动态编程** - 使用以前找到的子解决方案构建解决方案
* `B` [斐波那契数](src/algorithms/math/fibonacci)
* `B` [跳跃游戏](src/algorithms/uncategorized/jump-game)
* `B` [独特路径](src/algorithms/uncategorized/unique-paths)
* `B` [雨水收集](src/algorithms/uncategorized/rain-terraces) - 疏导雨水问题
* `B` [递归楼梯](src/algorithms/uncategorized/recursive-staircase) - 计算有共有多少种方法可以到达顶层 (4 种解题方案)
* `A` [莱温斯坦距离](src/algorithms/string/levenshtein-distance) - 两个序列之间的最小编辑距离
* `A` [最长公共子序列](src/algorithms/sets/longest-common-subsequence) (LCS)
* `A` [最长公共子串](src/algorithms/string/longest-common-substring)
@ -162,16 +180,18 @@ _Read this in other languages:_
* `A` [0-1背包问题](src/algorithms/sets/knapsack-problem)
* `A` [整数拆分](src/algorithms/math/integer-partition)
* `A` [最大子数列](src/algorithms/sets/maximum-subarray)
* `A` [弗洛伊德算法](src/algorithms/graph/floyd-warshall) - 找到所有顶点对之间的最短路径
* `A` [贝尔曼-福特算法](src/algorithms/graph/bellman-ford) - 找到所有图顶点的最短路径
* **回溯法** - 类似于 BF算法 试图产生所有可能的解决方案, 但每次生成解决方案测试如果它满足所有条件, 那么只有继续生成后续解决方案。 否则回溯并继续寻找不同路径的解决方案。
* `A` [弗洛伊德算法](src/algorithms/graph/floyd-warshall) - 找到所有顶点对之间的最短路径
* `A` [正则表达式匹配](src/algorithms/string/regular-expression-matching)
* **回溯法** - 类似于 `BF 算法` 试图产生所有可能的解决方案,但每次生成解决方案测试如果它满足所有条件,那么只有继续生成后续解决方案。否则回溯并继续寻找不同路径的解决方案。
* `B` [跳跃游戏](src/algorithms/uncategorized/jump-game)
* `B` [独特路径](src/algorithms/uncategorized/unique-paths)
* `A` [幂集](src/algorithms/sets/power-set) - 该集合的所有子集
* `A` [哈密顿图](src/algorithms/graph/hamiltonian-cycle) - 恰好访问每个顶点一次
* `A` [八皇后问题](src/algorithms/uncategorized/n-queens)
* `A` [骑士巡逻](src/algorithms/uncategorized/knight-tour)
* `A` [组合求和](src/algorithms/sets/combination-sum) - 从规定的总和中找出所有的组合
* **Branch & Bound**
* **Branch & Bound** - 记住在回溯搜索的每个阶段找到的成本最低的解决方案,并使用到目前为止找到的成本最小值作为下限。以便丢弃成本大于最小值的解决方案。通常,使用 BFS 遍历以及状态空间树的 DFS 遍历。
## 如何使用本仓库
@ -180,7 +200,16 @@ _Read this in other languages:_
npm install
```
**运行 ESLint**
检查代码质量
```
npm run lint
```
**执行测试**
```
npm test
```
@ -192,9 +221,9 @@ npm test -- 'LinkedList'
**Playground**
你可以在`./src/playground/playground.js`文件中操作数据结构与算法, 并在`./src/playground/__test__/playground.test.js`中编写测试。
你可以在 `./src/playground/playground.js` 文件中操作数据结构与算法,并在 `./src/playground/__test__/playground.test.js` 中编写测试。
然后, 只需运行以下命令来测试你的 Playground 是否按无误:
然后只需运行以下命令来测试你的 Playground 是否按无误:
```
npm test -- 'playground'
@ -228,26 +257,29 @@ npm test -- 'playground'
### 数据结构操作的复杂性
| 数据结构 | 连接 | 查找 | 插入 | 删除 |
| ----------------------- | :-------: | :-------: | :-------: | :-------: |
| **数组** | 1 | n | n | n |
| **栈** | n | n | 1 | 1 |
| **队列** | n | n | 1 | 1 |
| **链表** | n | n | 1 | 1 |
| **哈希表** | - | n | n | n |
| **二分查找树** | n | n | n | n |
| **B树** | log(n) | log(n) | log(n) | log(n) |
| **红黑树** | log(n) | log(n) | log(n) | log(n) |
| **AVL树** | log(n) | log(n) | log(n) | log(n) |
| 数据结构 | 连接 | 查找 | 插入 | 删除 | 备注 |
| -------------- | :----: | :----: | :----: | :----: | ---- |
| **数组** | 1 | n | n | n | |
| **栈** | n | n | 1 | 1 | |
| **队列** | n | n | 1 | 1 | |
| **链表** | n | n | 1 | 1 | |
| **哈希表** | - | n | n | n | 在完全哈希函数情况下,复杂度是 O(1 |
| **二分查找树** | n | n | n | n | 在平衡树情况下,复杂度是 O(log(n)) |
| **B 树** | log(n) | log(n) | log(n) | log(n) | |
| **红黑树** | log(n) | log(n) | log(n) | log(n) | |
| **AVL 树** | log(n) | log(n) | log(n) | log(n) | |
| **布隆过滤器** | - | 1 | 1 | - | 存在一定概率的判断错误(误判成存在) |
### 数组排序算法的复杂性
| 名称 | 最优 | 平均 | 最坏 | 内存 | 稳定 |
| --------------------- | :-------: | :-------: | :-----------: | :-------: | :-------: |
| **冒泡排序** | n | n^2 | n^2 | 1 | Yes |
| **插入排序** | n | n^2 | n^2 | 1 | Yes |
| **选择排序** | n^2 | n^2 | n^2 | 1 | No |
| **堆排序** | n log(n) | n log(n) | n log(n) | 1 | No |
| **归并排序** | n log(n) | n log(n) | n log(n) | n | Yes |
| **快速排序** | n log(n) | n log(n) | n^2 | log(n) | No |
| **希尔排序** | n log(n) | 取决于差距序列 | n (log(n))^2 | 1 | No |
| 名称 | 最优 | 平均 | 最坏 | 内存 | 稳定 | 备注 |
| --------------------- | :-------: | :-------: | :-----------: | :-------: | :-------: | --------------------- |
| **冒泡排序** | n | n^2 | n^2 | 1 | Yes | |
| **插入排序** | n | n^2 | n^2 | 1 | Yes | |
| **选择排序** | n^2 | n^2 | n^2 | 1 | No | |
| **堆排序** | n log(n) | n log(n) | n log(n) | 1 | No | |
| **归并排序** | n log(n) | n log(n) | n log(n) | n | Yes | |
| **快速排序** | n log(n) | n log(n) | n^2 | log(n) | No | 在 in-place 版本下,内存复杂度通常是 O(log(n)) |
| **希尔排序** | n log(n) | 取决于差距序列 | n (log(n))^2 | 1 | No | |
| **计数排序** | n + r | n + r | n + r | n + r | Yes | r - 数组里最大的数 |
| **基数排序** | n * k | n * k | n * k | n + k | Yes | k - 最长 key 的升序 |

View File

@ -10,6 +10,7 @@ _Read this in other languages:_
[_English_](https://github.com/trekhleb/javascript-algorithms/),
[_简体中文_](README.zh-CN.md),
[_한국어_](README.ko-KR.md),
[_日本語_](README.ja-JP.md),
[_Polski_](README.pl-PL.md),
[_Français_](README.fr-FR.md),
[_Español_](README.es-ES.md),

3167
package-lock.json generated

File diff suppressed because it is too large Load Diff

View File

@ -37,16 +37,16 @@
},
"homepage": "https://github.com/trekhleb/javascript-algorithms#readme",
"devDependencies": {
"@types/jest": "^23.1.4",
"@types/jest": "^23.3.10",
"babel-cli": "^6.26.0",
"babel-preset-env": "^1.7.0",
"eslint": "^4.19.1",
"eslint-config-airbnb": "^17.0.0",
"eslint-plugin-import": "^2.13.0",
"eslint-plugin-jest": "^21.17.0",
"eslint-plugin-jsx-a11y": "^6.1.0",
"eslint-plugin-react": "^7.10.0",
"jest": "^23.3.0",
"eslint": "^5.9.0",
"eslint-config-airbnb": "^17.1.0",
"eslint-plugin-import": "^2.14.0",
"eslint-plugin-jest": "^22.1.0",
"eslint-plugin-jsx-a11y": "^6.1.2",
"eslint-plugin-react": "^7.11.1",
"jest": "^23.6.0",
"pre-commit": "^1.2.2"
},
"dependencies": {}

View File

@ -1,5 +1,8 @@
# Factorial
_Read this in other languages:_
[_简体中文_](README.zh-CN.md),
In mathematics, the factorial of a non-negative integer `n`,
denoted by `n!`, is the product of all positive integers less
than or equal to `n`. For example:

View File

@ -0,0 +1,27 @@
# 阶乘
在数学上, 一个正整数 `n` 的阶乘 (写作 `n!`), 就是所有小于等于 `n` 的正整数的乘积. 比如:
```
5! = 5 * 4 * 3 * 2 * 1 = 120
```
| n | n! |
| ----- | --------------------------: |
| 0 | 1 |
| 1 | 1 |
| 2 | 2 |
| 3 | 6 |
| 4 | 24 |
| 5 | 120 |
| 6 | 720 |
| 7 | 5 040 |
| 8 | 40 320 |
| 9 | 362 880 |
| 10 | 3 628 800 |
| 11 | 39 916 800 |
| 12 | 479 001 600 |
| 13 | 6 227 020 800 |
| 14 | 87 178 291 200 |
| 15 | 1 307 674 368 000 |

View File

@ -10,12 +10,18 @@ import Comparator from '../../../utils/comparator/Comparator';
*/
export default function binarySearch(sortedArray, seekElement, comparatorCallback) {
// Let's create comparator from the comparatorCallback function.
// Comparator object will give us common comparison methods like equal() and lessThen().
const comparator = new Comparator(comparatorCallback);
// These two indices will contain current array (sub-array) boundaries.
let startIndex = 0;
let endIndex = sortedArray.length - 1;
// Let's continue to split array until boundaries are collapsed
// and there is nothing to split anymore.
while (startIndex <= endIndex) {
// Let's calculate the index of the middle element.
const middleIndex = startIndex + Math.floor((endIndex - startIndex) / 2);
// If we've found the element just return its position.
@ -33,5 +39,6 @@ export default function binarySearch(sortedArray, seekElement, comparatorCallbac
}
}
// Return -1 if we have not found anything.
return -1;
}

View File

@ -1,15 +1,27 @@
/**
* Generates Cartesian Product of two sets.
* @param {*[]} setA
* @param {*[]} setB
* @return {*[]}
*/
export default function cartesianProduct(setA, setB) {
// Check if input sets are not empty.
// Otherwise return null since we can't generate Cartesian Product out of them.
if (!setA || !setB || !setA.length || !setB.length) {
return null;
}
// Init product set.
const product = [];
// Now, let's go through all elements of a first and second set and form all possible pairs.
for (let indexA = 0; indexA < setA.length; indexA += 1) {
for (let indexB = 0; indexB < setB.length; indexB += 1) {
// Add current product pair to the product set.
product.push([setA[indexA], setB[indexB]]);
}
}
// Return cartesian product set.
return product;
}

View File

@ -4,6 +4,8 @@
* @return {*[]}
*/
export default function combineWithRepetitions(comboOptions, comboLength) {
// If the length of the combination is 1 then each element of the original array
// is a combination itself.
if (comboLength === 1) {
return comboOptions.map(comboOption => [comboOption]);
}
@ -11,14 +13,16 @@ export default function combineWithRepetitions(comboOptions, comboLength) {
// Init combinations array.
const combos = [];
// Eliminate characters one by one and concatenate them to
// combinations of smaller lengths.
// Remember characters one by one and concatenate them to combinations of smaller lengths.
// We don't extract elements here because the repetitions are allowed.
comboOptions.forEach((currentOption, optionIndex) => {
// Generate combinations of smaller size.
const smallerCombos = combineWithRepetitions(
comboOptions.slice(optionIndex),
comboLength - 1,
);
// Concatenate currentOption with all combinations of smaller size.
smallerCombos.forEach((smallerCombo) => {
combos.push([currentOption].concat(smallerCombo));
});

View File

@ -4,6 +4,8 @@
* @return {*[]}
*/
export default function combineWithoutRepetitions(comboOptions, comboLength) {
// If the length of the combination is 1 then each element of the original array
// is a combination itself.
if (comboLength === 1) {
return comboOptions.map(comboOption => [comboOption]);
}
@ -11,14 +13,16 @@ export default function combineWithoutRepetitions(comboOptions, comboLength) {
// Init combinations array.
const combos = [];
// Eliminate characters one by one and concatenate them to
// combinations of smaller lengths.
// Extract characters one by one and concatenate them to combinations of smaller lengths.
// We need to extract them because we don't want to have repetitions after concatenation.
comboOptions.forEach((currentOption, optionIndex) => {
// Generate combinations of smaller size.
const smallerCombos = combineWithoutRepetitions(
comboOptions.slice(optionIndex + 1),
comboLength - 1,
);
// Concatenate currentOption with all combinations of smaller size.
smallerCombos.forEach((smallerCombo) => {
combos.push([currentOption].concat(smallerCombo));
});

View File

@ -14,13 +14,14 @@ export default function permutateWithRepetitions(
// Init permutations array.
const permutations = [];
// Get smaller permutations.
const smallerPermutations = permutateWithRepetitions(
permutationOptions,
permutationLength - 1,
);
// Go through all options and join it to the smaller permutations.
permutationOptions.forEach((currentOption) => {
const smallerPermutations = permutateWithRepetitions(
permutationOptions,
permutationLength - 1,
);
smallerPermutations.forEach((smallerPermutation) => {
permutations.push([currentOption].concat(smallerPermutation));
});

View File

@ -47,6 +47,17 @@ what we need: it shows by its bits (`0` or `1`) whether to include related
element from the set or not. For example, for the set `{1, 2, 3}` the binary
number of `0b010` would mean that we need to include only `2` to the current set.
| | `abc` | Subset |
| :---: | :---: | :-----------: |
| `0` | `000` | `{}` |
| `1` | `001` | `{c}` |
| `2` | `010` | `{b}` |
| `3` | `011` | `{c, b}` |
| `4` | `100` | `{a}` |
| `5` | `101` | `{a, c}` |
| `6` | `110` | `{a, b}` |
| `7` | `111` | `{a, b, c}` |
> See [bwPowerSet.js](./bwPowerSet.js) file for bitwise solution.
### Backtracking Solution

View File

@ -6,16 +6,23 @@
* @return {*[][]} - All subsets of original set.
*/
function btPowerSetRecursive(originalSet, allSubsets = [[]], currentSubSet = [], startAt = 0) {
// In order to avoid duplication we need to start from next element every time we're forming a
// subset. If we will start from zero then we'll have duplicates like {3, 3, 3}.
// Let's iterate over originalSet elements that may be added to the subset
// without having duplicates. The value of startAt prevents adding the duplicates.
for (let position = startAt; position < originalSet.length; position += 1) {
// Let's push current element to the subset.
// Let's push current element to the subset
currentSubSet.push(originalSet[position]);
// Current subset is already valid so let's memorize it.
// We do array destruction here to save the clone of the currentSubSet.
// We need to save a clone since the original currentSubSet is going to be
// mutated in further recursive calls.
allSubsets.push([...currentSubSet]);
// Let's try to form all other subsets for the current subset.
// Let's try to generate all other subsets for the current subset.
// We're increasing the position by one to avoid duplicates in subset.
btPowerSetRecursive(originalSet, allSubsets, currentSubSet, position + 1);
// BACKTRACK. Exclude last element from the subset and try the next one.
// BACKTRACK. Exclude last element from the subset and try the next valid one.
currentSubSet.pop();
}

View File

@ -4,7 +4,7 @@
* @param {*[]} originalSet
* @return {*[][]}
*/
export default function powerSet(originalSet) {
export default function bwPowerSet(originalSet) {
const subSets = [];
// We will have 2^n possible combinations (where n is a length of original set).

View File

@ -19,9 +19,7 @@ export default class BubbleSort extends Sort {
// Swap elements if they are in wrong order.
if (this.comparator.lessThan(array[j + 1], array[j])) {
const tmp = array[j + 1];
array[j + 1] = array[j];
array[j] = tmp;
[array[j], array[j + 1]] = [array[j + 1], array[j]];
// Register the swap.
swapped = true;

View File

@ -3,9 +3,10 @@
Bubble sort, sometimes referred to as sinking sort, is a
simple sorting algorithm that repeatedly steps through
the list to be sorted, compares each pair of adjacent
items and swaps them if they are in the wrong order.
The pass through the list is repeated until no swaps
are needed, which indicates that the list is sorted.
items and swaps them if they are in the wrong order
(ascending or descending arrangement). The pass through
the list is repeated until no swaps are needed, which
indicates that the list is sorted.
![Algorithm Visualization](https://upload.wikimedia.org/wikipedia/commons/c/c8/Bubble-sort-example-300px.gif)

View File

@ -27,14 +27,10 @@ describe('CountingSort', () => {
const sorter = new CountingSort({ visitingCallback });
// Detect biggest number in array in prior.
const biggestElement = notSortedArr.reduce((accumulator, element) => {
return element > accumulator ? element : accumulator;
}, 0);
const biggestElement = Math.max(...notSortedArr);
// Detect smallest number in array in prior.
const smallestElement = notSortedArr.reduce((accumulator, element) => {
return element < accumulator ? element : accumulator;
}, 0);
const smallestElement = Math.min(...notSortedArr);
const sortedArray = sorter.sort(notSortedArr, smallestElement, biggestElement);

View File

@ -23,9 +23,7 @@ export default class SelectionSort extends Sort {
// If new minimum element has been found then swap it with current i-th element.
if (minIndex !== i) {
const tmp = array[i];
array[i] = array[minIndex];
array[minIndex] = tmp;
[array[i], array[minIndex]] = [array[minIndex], array[i]];
}
}

View File

@ -0,0 +1,21 @@
# Recursive Staircase Problem
## The Problem
There are `n` stairs, a person standing at the bottom wants to reach the top. The person can climb either `1` or `2` stairs at a time. _Count the number of ways, the person can reach the top._
![](https://cdncontribute.geeksforgeeks.org/wp-content/uploads/nth-stair.png)
## The Solution
This is an interesting problem because there are several ways of how it may be solved that illustrate different programming paradigms.
- [Brute Force Recursive Solution](./recursiveStaircaseBF.js) - Time: `O(2^n)`; Space: `O(1)`
- [Recursive Solution With Memoization](./recursiveStaircaseMEM.js) - Time: `O(n)`; Space: `O(n)`
- [Dynamic Programming Solution](./recursiveStaircaseDP.js) - Time: `O(n)`; Space: `O(n)`
- [Iterative Solution](./recursiveStaircaseIT.js) - Time: `O(n)`; Space: `O(1)`
## References
- [On YouTube by Gayle Laakmann McDowell](https://www.youtube.com/watch?v=eREiwuvzaUM&list=PLLXdhg_r2hKA7DPDsunoDZ-Z769jWn4R8&index=81&t=0s)
- [GeeksForGeeks](https://www.geeksforgeeks.org/count-ways-reach-nth-stair/)

View File

@ -0,0 +1,18 @@
import recursiveStaircaseBF from '../recursiveStaircaseBF';
describe('recursiveStaircaseBF', () => {
it('should calculate number of variants using Brute Force solution', () => {
expect(recursiveStaircaseBF(-1)).toBe(0);
expect(recursiveStaircaseBF(0)).toBe(0);
expect(recursiveStaircaseBF(1)).toBe(1);
expect(recursiveStaircaseBF(2)).toBe(2);
expect(recursiveStaircaseBF(3)).toBe(3);
expect(recursiveStaircaseBF(4)).toBe(5);
expect(recursiveStaircaseBF(5)).toBe(8);
expect(recursiveStaircaseBF(6)).toBe(13);
expect(recursiveStaircaseBF(7)).toBe(21);
expect(recursiveStaircaseBF(8)).toBe(34);
expect(recursiveStaircaseBF(9)).toBe(55);
expect(recursiveStaircaseBF(10)).toBe(89);
});
});

View File

@ -0,0 +1,18 @@
import recursiveStaircaseDP from '../recursiveStaircaseDP';
describe('recursiveStaircaseDP', () => {
it('should calculate number of variants using Dynamic Programming solution', () => {
expect(recursiveStaircaseDP(-1)).toBe(0);
expect(recursiveStaircaseDP(0)).toBe(0);
expect(recursiveStaircaseDP(1)).toBe(1);
expect(recursiveStaircaseDP(2)).toBe(2);
expect(recursiveStaircaseDP(3)).toBe(3);
expect(recursiveStaircaseDP(4)).toBe(5);
expect(recursiveStaircaseDP(5)).toBe(8);
expect(recursiveStaircaseDP(6)).toBe(13);
expect(recursiveStaircaseDP(7)).toBe(21);
expect(recursiveStaircaseDP(8)).toBe(34);
expect(recursiveStaircaseDP(9)).toBe(55);
expect(recursiveStaircaseDP(10)).toBe(89);
});
});

View File

@ -0,0 +1,18 @@
import recursiveStaircaseIT from '../recursiveStaircaseIT';
describe('recursiveStaircaseIT', () => {
it('should calculate number of variants using Iterative solution', () => {
expect(recursiveStaircaseIT(-1)).toBe(0);
expect(recursiveStaircaseIT(0)).toBe(0);
expect(recursiveStaircaseIT(1)).toBe(1);
expect(recursiveStaircaseIT(2)).toBe(2);
expect(recursiveStaircaseIT(3)).toBe(3);
expect(recursiveStaircaseIT(4)).toBe(5);
expect(recursiveStaircaseIT(5)).toBe(8);
expect(recursiveStaircaseIT(6)).toBe(13);
expect(recursiveStaircaseIT(7)).toBe(21);
expect(recursiveStaircaseIT(8)).toBe(34);
expect(recursiveStaircaseIT(9)).toBe(55);
expect(recursiveStaircaseIT(10)).toBe(89);
});
});

View File

@ -0,0 +1,18 @@
import recursiveStaircaseMEM from '../recursiveStaircaseMEM';
describe('recursiveStaircaseMEM', () => {
it('should calculate number of variants using Brute Force with Memoization', () => {
expect(recursiveStaircaseMEM(-1)).toBe(0);
expect(recursiveStaircaseMEM(0)).toBe(0);
expect(recursiveStaircaseMEM(1)).toBe(1);
expect(recursiveStaircaseMEM(2)).toBe(2);
expect(recursiveStaircaseMEM(3)).toBe(3);
expect(recursiveStaircaseMEM(4)).toBe(5);
expect(recursiveStaircaseMEM(5)).toBe(8);
expect(recursiveStaircaseMEM(6)).toBe(13);
expect(recursiveStaircaseMEM(7)).toBe(21);
expect(recursiveStaircaseMEM(8)).toBe(34);
expect(recursiveStaircaseMEM(9)).toBe(55);
expect(recursiveStaircaseMEM(10)).toBe(89);
});
});

View File

@ -0,0 +1,27 @@
/**
* Recursive Staircase Problem (Brute Force Solution).
*
* @param {number} stairsNum - Number of stairs to climb on.
* @return {number} - Number of ways to climb a staircase.
*/
export default function recursiveStaircaseBF(stairsNum) {
if (stairsNum <= 0) {
// There is no way to go down - you climb the stairs only upwards.
// Also if you're standing on the ground floor that you don't need to do any further steps.
return 0;
}
if (stairsNum === 1) {
// There is only one way to go to the first step.
return 1;
}
if (stairsNum === 2) {
// There are two ways to get to the second steps: (1 + 1) or (2).
return 2;
}
// Sum up how many steps we need to take after doing one step up with the number of
// steps we need to take after doing two steps up.
return recursiveStaircaseBF(stairsNum - 1) + recursiveStaircaseBF(stairsNum - 2);
}

View File

@ -0,0 +1,33 @@
/**
* Recursive Staircase Problem (Dynamic Programming Solution).
*
* @param {number} stairsNum - Number of stairs to climb on.
* @return {number} - Number of ways to climb a staircase.
*/
export default function recursiveStaircaseDP(stairsNum) {
if (stairsNum < 0) {
// There is no way to go down - you climb the stairs only upwards.
return 0;
}
// Init the steps vector that will hold all possible ways to get to the corresponding step.
const steps = new Array(stairsNum + 1).fill(0);
// Init the number of ways to get to the 0th, 1st and 2nd steps.
steps[0] = 0;
steps[1] = 1;
steps[2] = 2;
if (stairsNum <= 2) {
// Return the number of ways to get to the 0th or 1st or 2nd steps.
return steps[stairsNum];
}
// Calculate every next step based on two previous ones.
for (let currentStep = 3; currentStep <= stairsNum; currentStep += 1) {
steps[currentStep] = steps[currentStep - 1] + steps[currentStep - 2];
}
// Return possible ways to get to the requested step.
return steps[stairsNum];
}

View File

@ -0,0 +1,31 @@
/**
* Recursive Staircase Problem (Iterative Solution).
*
* @param {number} stairsNum - Number of stairs to climb on.
* @return {number} - Number of ways to climb a staircase.
*/
export default function recursiveStaircaseIT(stairsNum) {
if (stairsNum <= 0) {
// There is no way to go down - you climb the stairs only upwards.
// Also you don't need to do anything to stay on the 0th step.
return 0;
}
// Init the number of ways to get to the 0th, 1st and 2nd steps.
const steps = [1, 2];
if (stairsNum <= 2) {
// Return the number of possible ways of how to get to the 1st or 2nd steps.
return steps[stairsNum - 1];
}
// Calculate the number of ways to get to the n'th step based on previous ones.
// Comparing to Dynamic Programming solution we don't store info for all the steps but
// rather for two previous ones only.
for (let currentStep = 3; currentStep <= stairsNum; currentStep += 1) {
[steps[0], steps[1]] = [steps[1], steps[0] + steps[1]];
}
// Return possible ways to get to the requested step.
return steps[1];
}

View File

@ -0,0 +1,44 @@
/**
* Recursive Staircase Problem (Recursive Solution With Memoization).
*
* @param {number} totalStairs - Number of stairs to climb on.
* @return {number} - Number of ways to climb a staircase.
*/
export default function recursiveStaircaseMEM(totalStairs) {
// Memo table that will hold all recursively calculated results to avoid calculating them
// over and over again.
const memo = [];
// Recursive closure.
const getSteps = (stairsNum) => {
if (stairsNum <= 0) {
// There is no way to go down - you climb the stairs only upwards.
// Also if you're standing on the ground floor that you don't need to do any further steps.
return 0;
}
if (stairsNum === 1) {
// There is only one way to go to the first step.
return 1;
}
if (stairsNum === 2) {
// There are two ways to get to the second steps: (1 + 1) or (2).
return 2;
}
// Avoid recursion for the steps that we've calculated recently.
if (memo[stairsNum]) {
return memo[stairsNum];
}
// Sum up how many steps we need to take after doing one step up with the number of
// steps we need to take after doing two steps up.
memo[stairsNum] = getSteps(stairsNum - 1) + getSteps(stairsNum - 2);
return memo[stairsNum];
};
// Return possible ways to get to the requested step.
return getSteps(totalStairs);
}

View File

@ -243,9 +243,11 @@ export default class DoublyLinkedList {
while (currNode) {
// Store next node.
nextNode = currNode.next;
prevNode = currNode.previous;
// Change next node of the current node so it would link to previous node.
currNode.next = prevNode;
currNode.previous = nextNode;
// Move prevNode and currNode nodes one step forward.
prevNode = currNode;

View File

@ -1,5 +1,9 @@
# Doubly Linked List
_Read this in other languages:_
[_简体中文_](README.zh-CN.md),
[_Русский_](README.ru-RU.md)
In computer science, a **doubly linked list** is a linked data structure that
consists of a set of sequentially linked records called nodes. Each node contains
two fields, called links, that are references to the previous and to the next
@ -54,7 +58,7 @@ Remove(head, value)
head ← ø
tail ← ø
else
head ← head.Next
head ← head.next
head.previous ← ø
end if
return true

View File

@ -0,0 +1,108 @@
# Двусвязный список
**Двусвязный список** — связная структура данных в информатике, состоящая из набора
последовательно связанных записей, называемых узлами. Каждый узел содержит два поля,
называемых ссылками, которые указывают на предыдущий и последующий элементы в
последовательности узлов. Ссылка на предыдущий элемент корневого узла ссылка на
последующий элемент последнего узла, указывают на некого рода прерыватель, обычно
сторожевой узел или null, для облегчения обхода списка. Если в списке только один
сторожевой узел, тогда список циклически связана через него.
Двусвязный список можно представить, как два связных списка, которые образованны из
одних и тех же данных, но расположенных в противоположном порядке.
![Двусвязный список](https://upload.wikimedia.org/wikipedia/commons/5/5e/Doubly-linked-list.svg)
Две ссылки позволяют обходить список в обоих направлениях. Добавление и
удаление узла в двусвязном списке требует изменения большего количества ссылок,
чем аналогичные операции в связном списке. Однако данные операции проще и потенциально
более эффективны (для некорневых узлов) - при обходе не нужно следить за предыдущим
узлом или повторно обходить список в поиске предыдущего узла, плюс его ссылка
может быть изменена.
## Псевдокод основных операций
### Вставка
```text
Add(value)
Pre: value - добавляемое значение
Post: value помещено в конец списка
n ← node(value)
if head = ø
head ← n
tail ← n
else
n.previous ← tail
tail.next ← n
tail ← n
end if
end Add
```
### Удаление
```text
Remove(head, value)
Pre: head - первый узел в списке
value - значение, которое следует удалить
Post: true - value удалено из списка, иначе false
if head = ø
return false
end if
if value = head.value
if head = tail
head ← ø
tail ← ø
else
head ← head.next
head.previous ← ø
end if
return true
end if
n ← head.next
while n = ø and value = n.value
n ← n.next
end while
if n = tail
tail ← tail.previous
tail.next ← ø
return true
else if n = ø
n.previous.next ← n.next
n.next.previous ← n.previous
return true
end if
return false
end Remove
```
### Обратный обход
```text
ReverseTraversal(tail)
Pre: tail - конечный элемент обходимого списка
Post: элементы списка пройдены в обратном порядке
n ← tail
while n = ø
yield n.value
n ← n.previous
end while
end Reverse Traversal
```
## Сложность
## Временная сложность
| Чтение | Поиск | Вставка | Удаление |
| :-------: | :-------: | :-------: | :-------: |
| O(n) | O(n) | O(1) | O(1) |
### Пространственная сложность
O(n)
## Ссылки
- [Wikipedia](https://ru.wikipedia.org/wiki/%D0%A1%D0%B2%D1%8F%D0%B7%D0%BD%D1%8B%D0%B9_%D1%81%D0%BF%D0%B8%D1%81%D0%BE%D0%BA#%D0%94%D0%B2%D1%83%D1%81%D0%B2%D1%8F%D0%B7%D0%BD%D1%8B%D0%B9_%D1%81%D0%BF%D0%B8%D1%81%D0%BE%D0%BA_(%D0%B4%D0%B2%D1%83%D0%BD%D0%B0%D0%BF%D1%80%D0%B0%D0%B2%D0%BB%D0%B5%D0%BD%D0%BD%D1%8B%D0%B9_%D1%81%D0%B2%D1%8F%D0%B7%D0%BD%D1%8B%D0%B9_%D1%81%D0%BF%D0%B8%D1%81%D0%BE%D0%BA))
- [YouTube](https://www.youtube.com/watch?v=lQ-lPjbb9Ew)

View File

@ -45,7 +45,7 @@ Remove(head, value)
head ← ø
tail ← ø
else
head ← head.Next
head ← head.next
head.previous ← ø
end if
return true

View File

@ -236,22 +236,45 @@ describe('DoublyLinkedList', () => {
linkedList
.append(1)
.append(2)
.append(3);
.append(3)
.append(4);
expect(linkedList.toString()).toBe('1,2,3');
expect(linkedList.toString()).toBe('1,2,3,4');
expect(linkedList.head.value).toBe(1);
expect(linkedList.tail.value).toBe(3);
expect(linkedList.tail.value).toBe(4);
// Reverse linked list.
linkedList.reverse();
expect(linkedList.toString()).toBe('3,2,1');
expect(linkedList.head.value).toBe(3);
expect(linkedList.toString()).toBe('4,3,2,1');
expect(linkedList.head.previous).toBeNull();
expect(linkedList.head.value).toBe(4);
expect(linkedList.head.next.value).toBe(3);
expect(linkedList.head.next.next.value).toBe(2);
expect(linkedList.head.next.next.next.value).toBe(1);
expect(linkedList.tail.next).toBeNull();
expect(linkedList.tail.value).toBe(1);
expect(linkedList.tail.previous.value).toBe(2);
expect(linkedList.tail.previous.previous.value).toBe(3);
expect(linkedList.tail.previous.previous.previous.value).toBe(4);
// Reverse linked list back to initial state.
linkedList.reverse();
expect(linkedList.toString()).toBe('1,2,3');
expect(linkedList.toString()).toBe('1,2,3,4');
expect(linkedList.head.previous).toBeNull();
expect(linkedList.head.value).toBe(1);
expect(linkedList.tail.value).toBe(3);
expect(linkedList.head.next.value).toBe(2);
expect(linkedList.head.next.next.value).toBe(3);
expect(linkedList.head.next.next.next.value).toBe(4);
expect(linkedList.tail.next).toBeNull();
expect(linkedList.tail.value).toBe(4);
expect(linkedList.tail.previous.value).toBe(3);
expect(linkedList.tail.previous.previous.value).toBe(2);
expect(linkedList.tail.previous.previous.previous.value).toBe(1);
});
});

View File

@ -123,18 +123,6 @@ export default class Graph {
return vertex.findEdge(endVertex);
}
/**
* @param {string} vertexKey
* @returns {GraphVertex}
*/
findVertexByKey(vertexKey) {
if (this.vertices[vertexKey]) {
return this.vertices[vertexKey];
}
return null;
}
/**
* @return {number}
*/

View File

@ -32,14 +32,14 @@ describe('Graph', () => {
expect(graph.getAllVertices()[0]).toEqual(vertexA);
expect(graph.getAllVertices()[1]).toEqual(vertexB);
const graphVertexA = graph.findVertexByKey(vertexA.getKey());
const graphVertexB = graph.findVertexByKey(vertexB.getKey());
const graphVertexA = graph.getVertexByKey(vertexA.getKey());
const graphVertexB = graph.getVertexByKey(vertexB.getKey());
expect(graph.toString()).toBe('A,B');
expect(graphVertexA).toBeDefined();
expect(graphVertexB).toBeDefined();
expect(graph.findVertexByKey('not existing')).toBeNull();
expect(graph.getVertexByKey('not existing')).toBeUndefined();
expect(graphVertexA.getNeighbors().length).toBe(1);
expect(graphVertexA.getNeighbors()[0]).toEqual(vertexB);
@ -60,8 +60,8 @@ describe('Graph', () => {
graph.addEdge(edgeAB);
const graphVertexA = graph.findVertexByKey(vertexA.getKey());
const graphVertexB = graph.findVertexByKey(vertexB.getKey());
const graphVertexA = graph.getVertexByKey(vertexA.getKey());
const graphVertexB = graph.getVertexByKey(vertexB.getKey());
expect(graph.toString()).toBe('A,B');
expect(graphVertexA).toBeDefined();

View File

@ -1,5 +1,9 @@
# Linked List
_Read this in other languages:_
[_简体中文_](README.zh-CN.md),
[_Русский_](README.ru-RU.md)
In computer science, a **linked list** is a linear collection
of data elements, in which linear order is not given by
their physical placement in memory. Instead, each

View File

@ -0,0 +1,145 @@
# Связный список
Связный список — базовая динамическая структура данных в информатике, состоящая из узлов, каждый из которых содержит как собственно данные,так ссылку («связку») на следующий узел списка. Данная структура позволяет эффективно добавлять и удалять элементы на произвольной позиции в последовательности в процессе итерации. Более сложные варианты включают дополнительные ссылки, позволяющие эффективно добавлять и удалять произвольные элементы.
Принципиальным преимуществом перед массивом является структурная гибкость: порядок элементов связного списка может не совпадать с порядком расположения элементов данных в памяти компьютера, а порядок обхода списка всегда явно задаётся его внутренними связями. Суть преимущества состоит в том, что во многих языках создание массива требует указать его размер заранее. Связный список позволяет обойти это ограничение.
Недостатком связных списков является то, что время доступа линейно (и затруднительно для реализации конвейеров). Быстрый доступ(случайный) невозможен.
![Связный список](https://upload.wikimedia.org/wikipedia/commons/6/6d/Singly-linked-list.svg)
## Псевдокод основных операций
### Вставка
```text
Add(value)
Pre: value - добавляемое значение
Post: value помещено в конец списка
n ← node(value)
if head = ø
head ← n
tail ← n
else
tail.next ← n
tail ← n
end if
end Add
```
```text
Prepend(value)
Pre: value - добавляемое значение
Post: value помещено в начало списка
n ← node(value)
n.next ← head
head ← n
if tail = ø
tail ← n
end
end Prepend
```
### Поиск
```text
Contains(head, value)
Pre: head - первый узел в списке
value - значение, которое следует найти
Post: true - value найдено в списке, иначе false
n ← head
while n != ø and n.value != value
n ← n.next
end while
if n = ø
return false
end if
return true
end Contains
```
### Удаление
```text
Remove(head, value)
Pre: head - первый узел в списке
value - значение, которое следует удалить
Post: true - value удалено из списка, иначе false
if head = ø
return false
end if
n ← head
if n.value = value
if head = tail
head ← ø
tail ← ø
else
head ← head.next
end if
return true
end if
while n.next != ø and n.next.value != value
n ← n.next
end while
if n.next != ø
if n.next = tail
tail ← n
end if
n.next ← n.next.next
return true
end if
return false
end Remove
```
### Обход
```text
Traverse(head)
Pre: head - первый узел в списке
Post: элементы списка пройдены
n ← head
while n != ø
yield n.value
n ← n.next
end while
end Traverse
```
### Обратный обход
```text
ReverseTraversal(head, tail)
Pre: head и tail относятся к одному списку
Post: элементы списка пройдены в обратном порядке
if tail != ø
curr ← tail
while curr != head
prev ← head
while prev.next != curr
prev ← prev.next
end while
yield curr.value
curr ← prev
end while
yeild curr.value
end if
end ReverseTraversal
```
## Сложность
### Временная сложность
| Чтение | Поиск | Вставка | Удаление |
| :--------: | :-------: | :--------: | :-------: |
| O(n) | O(n) | O(1) | O(1) |
### Пространственная сложность
O(n)
## Ссылки
- [Wikipedia](https://ru.wikipedia.org/wiki/%D0%A1%D0%B2%D1%8F%D0%B7%D0%BD%D1%8B%D0%B9_%D1%81%D0%BF%D0%B8%D1%81%D0%BE%D0%BA)
- [YouTube](https://www.youtube.com/watch?v=KTpOalDwBjg)

View File

@ -28,7 +28,20 @@ Add(value)
end if
end Add
```
```
Prepend(value)
Pre: value is the value to add to the list
Post: value has been placed at the head of the list
n ← node(value)
n.next ← head
head ← n
if tail = ø
tail ← n
end
end Prepend
```
### 搜索
```text
@ -67,10 +80,10 @@ Remove(head, value)
end if
return true
end if
while n.next = ø and n.next.value = value
while n.next != ø and n.next.value != value
n ← n.next
end while
if n.next = ø
if n.next != ø
if n.next = tail
tail ← n
end if
@ -88,7 +101,7 @@ Traverse(head)
Pre: head is the head node in the list
Post: the items in the list have been traversed
n ← head
while n = 0
while n != 0
yield n.value
n ← n.next
end while
@ -101,11 +114,11 @@ end Traverse
ReverseTraversal(head, tail)
Pre: head and tail belong to the same list
Post: the items in the list have been traversed in reverse order
if tail = ø
if tail != ø
curr ← tail
while curr = head
while curr != head
prev ← head
while prev.next = curr
while prev.next != curr
prev ← prev.next
end while
yield curr.value

View File

@ -1,5 +1,9 @@
# Priority Queue
_Read this in other languages:_
[_简体中文_](README.zh-CN.md),
[_Русский_](README.ru-RU.md)
In computer science, a **priority queue** is an abstract data type
which is like a regular queue or stack data structure, but where
additionally each element has a "priority" associated with it.

View File

@ -0,0 +1,22 @@
# Очередь с приоритетом
Очередь с приоритетом (англ. priority queue) — абстрактный тип данных в информатике,
для каждого элемента которого можно вычислить его приоритет.
В очереди с приоритетами элемент с высоким приоритетом обслуживается раньше
элемента с низким приоритетом. Если два элемента имеют одинаковый приоритет, они
обслуживаются в соответствии с их порядком в очереди.
Очередь с приоритетом поддерживает две обязательные операции — добавить элемент и
извлечь максимум(минимум).
Хотя приоритетные очереди часто реализуются в виде куч(heaps), они
концептуально отличаются от куч. Очередь приоритетов является абстрактной
концепцией вроде «списка» или «карты»; так же, как список может быть реализован
в виде связного списка или массива, так и очередь с приоритетом может быть реализована
в виде кучи или множеством других методов, например в виде неупорядоченного массива.
## Ссылки
- [Wikipedia](https://ru.wikipedia.org/wiki/%D0%9E%D1%87%D0%B5%D1%80%D0%B5%D0%B4%D1%8C_%D1%81_%D0%BF%D1%80%D0%B8%D0%BE%D1%80%D0%B8%D1%82%D0%B5%D1%82%D0%BE%D0%BC_(%D0%BF%D1%80%D0%BE%D0%B3%D1%80%D0%B0%D0%BC%D0%BC%D0%B8%D1%80%D0%BE%D0%B2%D0%B0%D0%BD%D0%B8%D0%B5))
- [YouTube](https://www.youtube.com/watch?v=y_2toG5-j_M)

View File

@ -1,5 +1,9 @@
# Queue
_Read this in other languages:_
[_简体中文_](README.zh-CN.md),
[_Русский_](README.ru-RU.md)
In computer science, a **queue** is a particular kind of abstract data
type or collection in which the entities in the collection are
kept in order and the principle (or only) operations on the

View File

@ -0,0 +1,19 @@
# Очередь
Очередь (англ. queue) - структура данных в информатике, в которой элементы
хранятся в порядке их добавления. Добавление новых элементов(enqueue)
осуществляется в начало списка. А удаление элементов (dequeue)
осуществляется с конца. Таким образом очередь реализует принцип
"первым вошёл - первым вышел" (FIFO). Часто реализуется операция чтения
головного элемента (peek), которая возвращает первый в очереди элемент,
при этом не удаляя его. Очередь является примером линейной структуры
данных или последовательной коллекции.
Иллюстрация работы с очередью.
![Очередь](https://upload.wikimedia.org/wikipedia/commons/5/52/Data_Queue.svg)
## References
- [Wikipedia](https://ru.wikipedia.org/wiki/%D0%9E%D1%87%D0%B5%D1%80%D0%B5%D0%B4%D1%8C_(%D0%BF%D1%80%D0%BE%D0%B3%D1%80%D0%B0%D0%BC%D0%BC%D0%B8%D1%80%D0%BE%D0%B2%D0%B0%D0%BD%D0%B8%D0%B5))
- [YouTube](https://www.youtube.com/watch?v=GRsVMTlBIoE)

View File

@ -1,5 +1,9 @@
# Stack
_Read this in other languages:_
[_简体中文_](README.zh-CN.md),
[_Русский_](README.ru-RU.md)
In computer science, a **stack** is an abstract data type that serves
as a collection of elements, with two principal operations:
@ -13,7 +17,7 @@ the stack. The name "stack" for this type of structure comes
from the analogy to a set of physical items stacked on top of
each other, which makes it easy to take an item off the top
of the stack, while getting to an item deeper in the stack
may require taking off multiple other items first
may require taking off multiple other items first.
Simple representation of a stack runtime with push and pop operations.

View File

@ -0,0 +1,23 @@
# Стек
Стек (англ. stack — стопка) — абстрактный тип данных, представляющий собой
список элементов, организованных по принципу LIFO (последним пришёл — первым вышел).
Стек имеет две ключевые операции:
* **добавление (push)** элемента в конец стека, и
* **удаление (pop)**, последнего добавленного элемента.
Дополнительная операция чтения головного элемента (peek) даёт доступ
к последнему элементу стека без изменения самого стека.
Чаще всего принцип работы стека сравнивают со стопкой тарелок: чтобы взять вторую
сверху, нужно снять верхнюю.
Иллюстрация работы со стеком.
![Стек](https://upload.wikimedia.org/wikipedia/commons/b/b4/Lifo_stack.png)
## Ссылки
- [Wikipedia](https://ru.wikipedia.org/wiki/%D0%A1%D1%82%D0%B5%D0%BA)
- [YouTube](https://www.youtube.com/watch?v=tH8qi7lej5U)

View File

@ -1,6 +1,6 @@
# 栈
在计算机科学中, 一个 **栈(stack)** 一种抽象数据类型,用作表示元素的集合,具有两种主要操作:
在计算机科学中, 一个 **栈(stack)** 一种抽象数据类型,用作表示元素的集合,具有两种主要操作:
* **push**, 添加元素到栈的顶端(末尾);
* **pop**, 移除栈最顶端(末尾)的元素.

View File

@ -25,24 +25,24 @@ AVL tree with balance factors (green)
**Left-Left Rotation**
![Left-Left Rotation](http://btechsmartclass.com/DS/images/LL%20Rotation.png)
![Left-Left Rotation](http://btechsmartclass.com/data_structures/ds_images/LL%20Rotation.png)
**Right-Right Rotation**
![Right-Right Rotation](http://btechsmartclass.com/DS/images/RR%20Rotation.png)
![Right-Right Rotation](http://btechsmartclass.com/data_structures/ds_images/RR%20Rotation.png)
**Left-Right Rotation**
![Left-Right Rotation](http://btechsmartclass.com/DS/images/LR%20Rotation.png)
![Left-Right Rotation](http://btechsmartclass.com/data_structures/ds_images/LR%20Rotation.png)
**Right-Left Rotation**
![Right-Right Rotation](http://btechsmartclass.com/DS/images/RL%20Rotation.png)
![Right-Right Rotation](http://btechsmartclass.com/data_structures/ds_images/RL%20Rotation.png)
## References
* [Wikipedia](https://en.wikipedia.org/wiki/AVL_tree)
* [Tutorials Point](https://www.tutorialspoint.com/data_structures_algorithms/avl_tree_algorithm.htm)
* [BTech](http://btechsmartclass.com/DS/U5_T2.html)
* [BTech](http://btechsmartclass.com/data_structures/avl-trees.html)
* [AVL Tree Insertion on YouTube](https://www.youtube.com/watch?v=rbg7Qf8GkQ4&list=PLLXdhg_r2hKA7DPDsunoDZ-Z769jWn4R8&index=12&)
* [AVL Tree Interactive Visualisations](https://www.cs.usfca.edu/~galles/visualization/AVLtree.html)

View File

@ -103,19 +103,31 @@ remove(value)
else
parent.right ← nodeToRemove.right
end if
else if nodeToRemove.left = ø and nodeToRemove.right = ø
if nodeToRemove.value < parent.value
parent.left ← nodeToRemove.left
else
parent.right ← nodeToRemove.left
end if
else if nodeToRemove.left != ø and nodeToRemove.right != ø
next ← nodeToRemove.right
while next.left != ø
next ← next.left
end while
if next != nodeToRemove.right
remove(next.value)
nodeToRemove.value ← next.value
else
nodeToRemove.value ← next.value
nodeToRemove.right ← nodeToRemove.right.right
end if
else
largestValue ← nodeToRemove.left
while largestValue.right = ø
largestValue ← largestValue.right
end while
findParent(largestValue.value).right ← ø
nodeToRemove.value ← largestValue.value
if nodeToRemove.left = ø
next ← nodeToRemove.right
else
next ← nodeToRemove.left
end if
if root = nodeToRemove
root = next
else if parent.left = nodeToRemove
parent.left = next
else if parent.right = nodeToRemove
parent.right = next
end if
end if
count ← count - 1
return true

View File

@ -60,7 +60,7 @@ export default class FenwickTree {
*/
queryRange(leftIndex, rightIndex) {
if (leftIndex > rightIndex) {
throw new Error('Left index can not be greater then right one');
throw new Error('Left index can not be greater than right one');
}
if (leftIndex === 1) {

View File

@ -1,12 +1,14 @@
export default class Comparator {
/**
* @param {function(a: *, b: *)} [compareFunction]
* @param {function(a: *, b: *)} [compareFunction] - It may be custom compare function that, let's
* say may compare custom objects together.
*/
constructor(compareFunction) {
this.compare = compareFunction || Comparator.defaultCompareFunction;
}
/**
* Default comparison function. It just assumes that "a" and "b" are strings or numbers.
* @param {(string|number)} a
* @param {(string|number)} b
* @returns {number}
@ -19,26 +21,59 @@ export default class Comparator {
return a < b ? -1 : 1;
}
/**
* Checks if two variables are equal.
* @param {*} a
* @param {*} b
* @return {boolean}
*/
equal(a, b) {
return this.compare(a, b) === 0;
}
/**
* Checks if variable "a" is less than "b".
* @param {*} a
* @param {*} b
* @return {boolean}
*/
lessThan(a, b) {
return this.compare(a, b) < 0;
}
/**
* Checks if variable "a" is greater than "b".
* @param {*} a
* @param {*} b
* @return {boolean}
*/
greaterThan(a, b) {
return this.compare(a, b) > 0;
}
/**
* Checks if variable "a" is less than or equal to "b".
* @param {*} a
* @param {*} b
* @return {boolean}
*/
lessThanOrEqual(a, b) {
return this.lessThan(a, b) || this.equal(a, b);
}
/**
* Checks if variable "a" is greater than or equal to "b".
* @param {*} a
* @param {*} b
* @return {boolean}
*/
greaterThanOrEqual(a, b) {
return this.greaterThan(a, b) || this.equal(a, b);
}
/**
* Reverses the comparison order.
*/
reverse() {
const compareOriginal = this.compare;
this.compare = (a, b) => compareOriginal(b, a);