mirror of
https://github.moeyy.xyz/https://github.com/trekhleb/javascript-algorithms.git
synced 2024-11-14 23:12:58 +08:00
Compare commits
1 Commits
5a7147b83b
...
1f2fb041d7
Author | SHA1 | Date | |
---|---|---|---|
|
1f2fb041d7 |
@ -12,7 +12,6 @@
|
|||||||
"arrow-body-style": "off",
|
"arrow-body-style": "off",
|
||||||
"no-loop-func": "off"
|
"no-loop-func": "off"
|
||||||
},
|
},
|
||||||
"ignorePatterns": ["*.md", "*.png", "*.jpeg", "*.jpg"],
|
|
||||||
"settings": {
|
"settings": {
|
||||||
"react": {
|
"react": {
|
||||||
"version": "18.2.0"
|
"version": "18.2.0"
|
||||||
|
@ -3,7 +3,7 @@
|
|||||||
[![Build Status](https://travis-ci.org/trekhleb/javascript-algorithms.svg?branch=master)](https://travis-ci.org/trekhleb/javascript-algorithms)
|
[![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)
|
[![codecov](https://codecov.io/gh/trekhleb/javascript-algorithms/branch/master/graph/badge.svg)](https://codecov.io/gh/trekhleb/javascript-algorithms)
|
||||||
|
|
||||||
تحتوي هذه المقالة على أمثلة عديدة تستند إلى الخوارزميات الشائعة وهياكل البيانات في الجافا سكريبت.
|
تحتوي هذا مقالة على أمثلة عديدة تستند إلى الخوارزميات الشائعة وهياكل البيانات في الجافا سكريبت.
|
||||||
|
|
||||||
كل خوارزمية وهياكل البيانات لها برنامج README منفصل خاص بها
|
كل خوارزمية وهياكل البيانات لها برنامج README منفصل خاص بها
|
||||||
مع التفسيرات والروابط ذات الصلة لمزيد من القراءة (بما في ذلك تلك
|
مع التفسيرات والروابط ذات الصلة لمزيد من القراءة (بما في ذلك تلك
|
||||||
|
@ -70,7 +70,7 @@ definen con precisión una secuencia de operaciones.
|
|||||||
* **Matemáticas**
|
* **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` [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` [Factorial](src/algorithms/math/factorial)
|
||||||
* `P` [Sucesión de Fibonacci](src/algorithms/math/fibonacci)
|
* `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` [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` [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` [Mínimo común múltiplo](src/algorithms/math/least-common-multiple) (MCM)
|
||||||
|
@ -1,27 +0,0 @@
|
|||||||
# Búsqueda binaria
|
|
||||||
|
|
||||||
_Lea esto en otros idiomas:_
|
|
||||||
[English](README.md)
|
|
||||||
[Português brasileiro](README.pt-BR.md).
|
|
||||||
|
|
||||||
En informática, la búsqueda binaria, también conocida como búsqueda de medio intervalo
|
|
||||||
búsqueda, búsqueda logarítmica, o corte binario, es un algoritmo de búsqueda
|
|
||||||
que encuentra la posición de un valor objetivo dentro de una matriz
|
|
||||||
ordenada. La búsqueda binaria compara el valor objetivo con el elemento central
|
|
||||||
de la matriz; si son desiguales, se elimina la mitad en la que
|
|
||||||
la mitad en la que no puede estar el objetivo se elimina y la búsqueda continúa
|
|
||||||
en la mitad restante hasta que tenga éxito. Si la búsqueda
|
|
||||||
termina con la mitad restante vacía, el objetivo no está
|
|
||||||
en la matriz.
|
|
||||||
|
|
||||||
![Búsqueda binaria](https://upload.wikimedia.org/wikipedia/commons/8/83/Binary_Search_Depiction.svg)
|
|
||||||
|
|
||||||
## Complejidad
|
|
||||||
|
|
||||||
**Complejidad de tiempo**: `O(log(n))` - ya que dividimos el área de búsqueda en dos para cada
|
|
||||||
siguiente iteración.
|
|
||||||
|
|
||||||
## Referencias
|
|
||||||
|
|
||||||
- [Wikipedia](https://en.wikipedia.org/wiki/Binary_search_algorithm)
|
|
||||||
- [YouTube](https://www.youtube.com/watch?v=P3YID7liBug&index=29&list=PLLXdhg_r2hKA7DPDsunoDZ-Z769jWn4R8)
|
|
@ -2,7 +2,6 @@
|
|||||||
|
|
||||||
_Read this in other languages:_
|
_Read this in other languages:_
|
||||||
[Português brasileiro](README.pt-BR.md).
|
[Português brasileiro](README.pt-BR.md).
|
||||||
[Español](README.es-ES.md).
|
|
||||||
|
|
||||||
In computer science, binary search, also known as half-interval
|
In computer science, binary search, also known as half-interval
|
||||||
search, logarithmic search, or binary chop, is a search algorithm
|
search, logarithmic search, or binary chop, is a search algorithm
|
||||||
|
@ -2,7 +2,6 @@
|
|||||||
|
|
||||||
_Leia isso em outras línguas:_
|
_Leia isso em outras línguas:_
|
||||||
[english](README.md).
|
[english](README.md).
|
||||||
[Español](README.es-ES.md).
|
|
||||||
|
|
||||||
Em ciência da computação, busca binária, também conhecida como busca de meio-intervalo, busca logarítmica ou corte binário, é um algoritmo de pesquisa
|
Em ciência da computação, busca binária, também conhecida como busca de meio-intervalo, busca logarítmica ou corte binário, é um algoritmo de pesquisa
|
||||||
que encontra a posição de um elemento alvo dentro de um
|
que encontra a posição de um elemento alvo dentro de um
|
||||||
|
@ -7,9 +7,9 @@ _Lee este artículo en otros idiomas:_
|
|||||||
[_Português_](README.pt-BR.md)
|
[_Português_](README.pt-BR.md)
|
||||||
[_English_](README.md)
|
[_English_](README.md)
|
||||||
|
|
||||||
En ciencias de la computación una **lista enlazada** es una colección lineal
|
En ciencias de la computaciòn una **lista enlazada** es una coleccion linear
|
||||||
de elementos, en los cuales el orden lineal no es dado por
|
de elementos de datos, en los cuales el orden linear no es dado por
|
||||||
su posición física en memoria. En cambio, cada
|
su posciòn fisica en memoria. En cambio, cada
|
||||||
elemento señala al siguiente. Es una estructura de datos
|
elemento señala al siguiente. Es una estructura de datos
|
||||||
que consiste en un grupo de nodos los cuales juntos representan
|
que consiste en un grupo de nodos los cuales juntos representan
|
||||||
una secuencia. En su forma más sencilla, cada nodo está
|
una secuencia. En su forma más sencilla, cada nodo está
|
||||||
@ -19,10 +19,10 @@ permite la inserción o eliminación de elementos
|
|||||||
desde cualquier posición en la secuencia durante la iteración.
|
desde cualquier posición en la secuencia durante la iteración.
|
||||||
Las variantes más complejas agregan enlaces adicionales, permitiendo
|
Las variantes más complejas agregan enlaces adicionales, permitiendo
|
||||||
una eficiente inserción o eliminación desde referencias arbitrarias
|
una eficiente inserción o eliminación desde referencias arbitrarias
|
||||||
del elemento. Una desventaja de las listas enlazadas es que el tiempo de
|
del elemento. Una desventaja de las listas lazadas es que el tiempo de
|
||||||
acceso es lineal (y difícil de canalizar). Un acceso
|
acceso es lineal (y difícil de canalizar). Un acceso
|
||||||
más rápido, como un acceso aleatorio, no es factible. Los arreglos
|
más rápido, como un acceso aleatorio, no es factible. Los arreglos
|
||||||
tienen una mejor localización en caché comparados con las listas enlazadas.
|
tienen una mejor locazion en caché comparados con las listas lazadas.
|
||||||
|
|
||||||
![Linked List](./images/linked-list.jpeg)
|
![Linked List](./images/linked-list.jpeg)
|
||||||
|
|
||||||
@ -112,7 +112,7 @@ Remove(head, value)
|
|||||||
end Remove
|
end Remove
|
||||||
```
|
```
|
||||||
|
|
||||||
### Atravesar
|
### Atrevesar
|
||||||
|
|
||||||
```text
|
```text
|
||||||
Traverse(head)
|
Traverse(head)
|
||||||
|
@ -1,10 +1,10 @@
|
|||||||
# Зв'язаний список
|
# Зв'язаний список
|
||||||
|
|
||||||
Зв'язаний список — базова динамічна структура даних в інформатиці, що складається з вузлів, кожен з яких містить як дані, так і посилання («зв'язку») на наступний вузол списку. Ця структура даних дозволяє ефективно додавати та видаляти елементи на довільній позиції у послідовності у процесі ітерації. Більш складні варіанти включають додаткові посилання, що дозволяють ефективно додавати та видаляти довільні елементи.
|
Зв'язаний список — базова динамічна структура даних в інформатиці, що складається з вузлів, кожен з яких містить як дані, так посилання («зв'язку») на наступний вузол списку. Дана структура дозволяє ефективно додавати та видаляти елементи на довільній позиції у послідовності у процесі ітерації. Більш складні варіанти включають додаткові посилання, що дозволяють ефективно додавати та видаляти довільні елементи.
|
||||||
|
|
||||||
Принциповою перевагою перед масивом є структурна гнучкість: порядок елементів зв'язаного списку може збігатися з порядком розташування елементів даних у пам'яті комп'ютера, а порядок обходу списку завжди явно задається його внутрішніми зв'язками. Це важливо, бо у багатьох мовах створення масиву вимагає вказати його розмір заздалегідь. Зв'язаний список дозволяє обійти це обмеження.
|
Принциповою перевагою перед масивом є структурна гнучкість: порядок елементів зв'язкового списку може збігатися з порядком розташування елементів даних у пам'яті комп'ютера, а порядок обходу списку завжди явно задається його внутрішніми зв'язками. Суть переваги у тому, що у багатьох мовах створення масиву вимагає вказати його заздалегідь. Зв'язковий список дозволяє обійти це обмеження.
|
||||||
|
|
||||||
Недоліком зв'язаних списків є те, що час доступу є лінійним (і важко для реалізації конвеєрів). Неможливий швидкий доступ (випадковий).
|
Недоліком зв'язкових списків є те, що час доступу є лінійним (і важко для реалізації конвеєрів). Неможливий швидкий доступ (випадковий).
|
||||||
|
|
||||||
![Linked List](./images/linked-list.jpeg)
|
![Linked List](./images/linked-list.jpeg)
|
||||||
|
|
||||||
@ -17,7 +17,7 @@
|
|||||||
```text
|
```text
|
||||||
Add(value)
|
Add(value)
|
||||||
Pre: value - значення, що додається
|
Pre: value - значення, що додається
|
||||||
Post: value додано в кінець списку
|
Post: value поміщено в кінець списку
|
||||||
n ← node(value)
|
n ← node(value)
|
||||||
if head = ø
|
if head = ø
|
||||||
head ← n
|
head ← n
|
||||||
@ -32,7 +32,7 @@ end Add
|
|||||||
```text
|
```text
|
||||||
Prepend(value)
|
Prepend(value)
|
||||||
Pre: value - значення, що додається
|
Pre: value - значення, що додається
|
||||||
Post: value додано на початку списку
|
Post: value поміщено на початок списку
|
||||||
n ← node(value)
|
n ← node(value)
|
||||||
n.next ← head
|
n.next ← head
|
||||||
head ← n
|
head ← n
|
||||||
@ -42,7 +42,7 @@ Prepend(value)
|
|||||||
end Prepend
|
end Prepend
|
||||||
```
|
```
|
||||||
|
|
||||||
### Пошук
|
### Поиск
|
||||||
|
|
||||||
```text
|
```text
|
||||||
Contains(head, value)
|
Contains(head, value)
|
||||||
@ -60,7 +60,7 @@ Contains(head, value)
|
|||||||
end Contains
|
end Contains
|
||||||
```
|
```
|
||||||
|
|
||||||
### Видалення
|
### Вилучення
|
||||||
|
|
||||||
```text
|
```text
|
||||||
Remove(head, value)
|
Remove(head, value)
|
||||||
@ -94,7 +94,7 @@ Remove(head, value)
|
|||||||
end Remove
|
end Remove
|
||||||
```
|
```
|
||||||
|
|
||||||
### Обхід
|
### Обход
|
||||||
|
|
||||||
```text
|
```text
|
||||||
Traverse(head)
|
Traverse(head)
|
||||||
@ -108,12 +108,12 @@ Traverse(head)
|
|||||||
end Traverse
|
end Traverse
|
||||||
```
|
```
|
||||||
|
|
||||||
### Зворотній обхід
|
### Зворотний обхід
|
||||||
|
|
||||||
```text
|
```text
|
||||||
ReverseTraversal(head, tail)
|
ReverseTraversal(head, tail)
|
||||||
Pre: head і tail відносяться до одного списку
|
Pre: head и tail відносяться до одного списку
|
||||||
Post: елементи списку пройдено у зворотньому порядку
|
Post: елементи списку пройдено у зворотному порядку
|
||||||
if tail != ø
|
if tail != ø
|
||||||
curr ← tail
|
curr ← tail
|
||||||
while curr != head
|
while curr != head
|
||||||
@ -131,7 +131,7 @@ end ReverseTraversal
|
|||||||
|
|
||||||
## Складність
|
## Складність
|
||||||
|
|
||||||
### Часова складність
|
### Тимчасова складність
|
||||||
|
|
||||||
| Читання | Пошук | Вставка | Вилучення |
|
| Читання | Пошук | Вставка | Вилучення |
|
||||||
| :--------: | :-------: | :--------: | :-------: |
|
| :--------: | :-------: | :--------: | :-------: |
|
||||||
@ -143,5 +143,5 @@ O(n)
|
|||||||
|
|
||||||
## Посилання
|
## Посилання
|
||||||
|
|
||||||
- [Wikipedia](https://uk.wikipedia.org/wiki/Зв'язаний_список)
|
- [Wikipedia](https://uk.wikipedia.org/wiki/%D0%97%D0%B2%27%D1%8F%D0%B7%D0%B0%D0%BD%D0%B8%D0%B9_%D1%81%D0%BF%D0%B8%D1%81%D0%BE%D0%BA)
|
||||||
- [YouTube](https://www.youtube.com/watch?v=6snsMa4E1Os)
|
- [YouTube](https://www.youtube.com/watch?v=6snsMa4E1Os)
|
||||||
|
@ -1,51 +0,0 @@
|
|||||||
# LRU 캐시 알고리즘
|
|
||||||
|
|
||||||
**LRU 캐시 알고리즘** 은 사용된 순서대로 아이템을 정리함으로써, 오랜 시간 동안 사용되지 않은 아이템을 빠르게 찾아낼 수 있도록 한다.
|
|
||||||
|
|
||||||
한방향으로만 옷을 걸 수 있는 옷걸이 행거를 생각해봅시다. 가장 오랫동안 입지 않은 옷을 찾기 위해서는, 행거의 반대쪽 끝을 보면 됩니다.
|
|
||||||
|
|
||||||
## 문제 정의
|
|
||||||
|
|
||||||
LRUCache 클래스를 구현해봅시다:
|
|
||||||
|
|
||||||
- `LRUCache(int capacity)` LRU 캐시를 **양수** 의 `capacity` 로 초기화합니다.
|
|
||||||
- `int get(int key)` `key` 가 존재할 경우 `key` 값을 반환하고, 그렇지 않으면 `undefined` 를 반환합니다.
|
|
||||||
- `void set(int key, int value)` `key` 가 존재할 경우 `key` 값을 업데이트 하고, 그렇지 않으면 `key-value` 쌍을 캐시에 추가합니다. 만약 이 동작으로 인해 키 개수가 `capacity` 를 넘는 경우, 가장 오래된 키 값을 **제거** 합니다.
|
|
||||||
|
|
||||||
`get()` 과 `set()` 함수는 무조건 평균 `O(1)` 의 시간 복잡도 내에 실행되어야 합니다.
|
|
||||||
|
|
||||||
## 구현
|
|
||||||
|
|
||||||
### 버전 1: 더블 링크드 리스트 + 해시맵
|
|
||||||
|
|
||||||
[LRUCache.js](./LRUCache.js) 에서 `LRUCache` 구현체 예시를 확인할 수 있습니다. 예시에서는 (평균적으로) 빠른 `O(1)` 캐시 아이템 접근을 위해 `HashMap` 을 사용했고, (평균적으로) 빠른 `O(1)` 캐시 아이템 수정과 제거를 위해 `DoublyLinkedList` 를 사용했습니다. (허용된 최대의 캐시 용량을 유지하기 위해)
|
|
||||||
|
|
||||||
![Linked List](./images/lru-cache.jpg)
|
|
||||||
|
|
||||||
_[okso.app](https://okso.app) 으로 만듦_
|
|
||||||
|
|
||||||
LRU 캐시가 어떻게 작동하는지 더 많은 예시로 확인하고 싶다면 LRUCache.test.js](./**test**/LRUCache.test.js) 파일을 참고하세요.
|
|
||||||
|
|
||||||
### 버전 2: 정렬된 맵
|
|
||||||
|
|
||||||
더블 링크드 리스트로 구현한 첫번째 예시는 어떻게 평균 `O(1)` 시간 복잡도가 `set()` 과 `get()` 으로 나올 수 있는지 학습 목적과 이해를 돕기 위해 좋은 예시입니다.
|
|
||||||
|
|
||||||
그러나, 더 쉬운 방법은 자바스크립트의 [Map](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Map) 객체를 사용하는 것입니다. 이 `Map` 객체는 키-값 쌍과 키를 **추가하는 순서 원본** 을 지닙니다. 우리는 이걸 아이템을 제거하거나 다시 추가하면서 맵의 "가장 마지막" 동작에서 최근에 사용된 아이템을 유지하기 위해 사용할 수 있습니다. `Map` 의 시작점에 있는 아이템은 캐시 용량이 넘칠 경우 가장 먼저 제거되는 대상입니다. 아이템의 순서는 `map.keys()` 와 같은 `IterableIterator` 을 사용해 확인할 수 있습니다.
|
|
||||||
|
|
||||||
해당 구현체는 [LRUCacheOnMap.js](./LRUCacheOnMap.js) 의 `LRUCacheOnMap` 예시에서 확인할 수 있습니다.
|
|
||||||
|
|
||||||
이 LRU 캐시 방식이 어떻게 작동하는지 더 많은 테스트 케이스를 확인하고 싶다면 [LRUCacheOnMap.test.js](./__test__/LRUCacheOnMap.test.js) 파일을 참고하세요.
|
|
||||||
|
|
||||||
## 복잡도
|
|
||||||
|
|
||||||
| | 평균 |
|
|
||||||
| --------------- | ------ |
|
|
||||||
| 공간 | `O(n)` |
|
|
||||||
| 아이템 찾기 | `O(1)` |
|
|
||||||
| 아이템 설정하기 | `O(1)` |
|
|
||||||
|
|
||||||
## 참조
|
|
||||||
|
|
||||||
- [LRU Cache on LeetCode](https://leetcode.com/problems/lru-cache/solutions/244744/lru-cache/)
|
|
||||||
- [LRU Cache on InterviewCake](https://www.interviewcake.com/concept/java/lru-cache)
|
|
||||||
- [LRU Cache on Wiki](https://en.wikipedia.org/wiki/Cache_replacement_policies)
|
|
@ -1,8 +1,5 @@
|
|||||||
# Least Recently Used (LRU) Cache
|
# Least Recently Used (LRU) Cache
|
||||||
|
|
||||||
_Read this in other languages:_
|
|
||||||
[한국어](README.ko-KR.md),
|
|
||||||
|
|
||||||
A **Least Recently Used (LRU) Cache** organizes items in order of use, allowing you to quickly identify which item hasn't been used for the longest amount of time.
|
A **Least Recently Used (LRU) Cache** organizes items in order of use, allowing you to quickly identify which item hasn't been used for the longest amount of time.
|
||||||
|
|
||||||
Picture a clothes rack, where clothes are always hung up on one side. To find the least-recently used item, look at the item on the other end of the rack.
|
Picture a clothes rack, where clothes are always hung up on one side. To find the least-recently used item, look at the item on the other end of the rack.
|
||||||
@ -25,7 +22,7 @@ See the `LRUCache` implementation example in [LRUCache.js](./LRUCache.js). The s
|
|||||||
|
|
||||||
![Linked List](./images/lru-cache.jpg)
|
![Linked List](./images/lru-cache.jpg)
|
||||||
|
|
||||||
_Made with [okso.app](https://okso.app)_
|
*Made with [okso.app](https://okso.app)*
|
||||||
|
|
||||||
You may also find more test-case examples of how the LRU Cache works in [LRUCache.test.js](./__test__/LRUCache.test.js) file.
|
You may also find more test-case examples of how the LRU Cache works in [LRUCache.test.js](./__test__/LRUCache.test.js) file.
|
||||||
|
|
||||||
@ -41,11 +38,11 @@ You may also find more test-case examples of how the LRU Cache works in [LRUCach
|
|||||||
|
|
||||||
## Complexities
|
## Complexities
|
||||||
|
|
||||||
| | Average |
|
| | Average |
|
||||||
| -------- | ------- |
|
|---|---|
|
||||||
| Space | `O(n)` |
|
| Space |`O(n)`|
|
||||||
| Get item | `O(1)` |
|
| Get item | `O(1)` |
|
||||||
| Set item | `O(1)` |
|
| Set item | `O(1)` |
|
||||||
|
|
||||||
## References
|
## References
|
||||||
|
|
||||||
|
@ -10,8 +10,8 @@
|
|||||||
Додаткова операція для читання головного елемента (peek) дає доступ
|
Додаткова операція для читання головного елемента (peek) дає доступ
|
||||||
до останнього елементу стека без зміни самого стека.
|
до останнього елементу стека без зміни самого стека.
|
||||||
|
|
||||||
Найчастіше принцип роботи стека порівнюють із стопкою тарілок: щоб узяти другу
|
Найчастіше принцип роботи стека порівнюють зі чаркою тарілок: щоб узяти другу
|
||||||
зверху потрібно спочатку зняти верхню.
|
зверху потрібно зняти верхню.
|
||||||
|
|
||||||
Ілюстрація роботи зі стеком.
|
Ілюстрація роботи зі стеком.
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user