算法总结
数学
求斐波那契数列任意一位的值
#include <iostream>
long long getFibonacci(int n) {
if (n <= 0) throw -1;
if (n == 1 || n == 2)
return 1;
long long prev2 = 1; // F(1)
long long prev1 = 1; // F(2)
long long current = 0;
for (int i = 3; i <= n; ++i) {
current = prev1 + prev2;
prev2 = prev1;
prev1 = current;
}
return current;
}
int main() {
// 1 1 2 3 5 8
std::cout << getFibonacci(6) << std::endl;
}
字符串处理
逆转字符串
将字符串倒序输出
function reverseString(str: string) {
return [...str].reverse().join('');
}
console.log(reverseString("hello")); // "olleh"
void reverseString(std::string &s) {
int left = 0;
int right = s.length() - 1;
while (left < right) {
std::swap(s[left], s[right]);
left++;
right--;
}
}
int main() {
std::string s = "hello";
// std::reverse(s.begin(), s.end());
reverseString(s);
std::cout << s << std::endl; // olleh
return 0;
}
统计字符串中出现最多的字符
寻找字符串中重复次数最多的字符
function maxOccurChar(str: string) {
const map = new Map();
let maxChar = '';
let maxCount = 0;
for (let char of str) {
let count = (map.get(char) || 0) + 1;
map.set(char, count);
if (count > maxCount) {
maxCount = count;
maxChar = char;
}
}
return maxChar;
}
console.log(maxOccurChar("aaabbc")); // a
char maxOccurChar(const std::string &s) {
std::unordered_map<char, int> map ;
char maxChar = 0;
int maxCount = 0;
for (const char & c : s) {
map[c] ++;
if (map[c] > maxCount) {
maxCount = map[c];
maxChar = c;
}
}
return maxChar;
}
int main() {
std::cout << maxOccurChar("aaabbc") << std::endl; // true
return 0;
}
验证回文串
判断字符串忽略大小写和非字母数字字符后,是否正反读都一样
function isPalindrome(s: string) {
const cleaned = s.replace(/[^a-zA-Z0-9]/g, '').toLowerCase();
let left = 0, right = cleaned.length - 1;
while (left < right) {
if (cleaned[left] !== cleaned[right]) return false;
left++;
right--;
}
return true;
}
console.log(isPalindrome("abbba"));
bool isPalindrome(const std::string &s) {
int left = 0;
int right = s.length() - 1;
while (left < right) {
while (left < right && !std::isalnum(s[left]))
left++;
while (left < right && !std::isalnum(s[right]))
right--;
if (std::tolower(s[left]) != std::tolower(s[right])) {
return false;
}
left++;
right--;
}
return true;
}
int main() {
bool ret = isPalindrome("A man, a plan, a canal: Panama");
std::cout << std::boolalpha << ret << std::endl; // true
return 0;
}
Atoi
#include <iostream>
#include <string>
int myAtoi(const std::string &str) {
if (str.empty())
return 0;
int i = 0;
int sign = 1;
long long res = 0; // 使用 long long 防止溢出
while (i < str.length() && str[i] == ' ') {
i++;
}
// 处理符号位
if (i < str.length() && (str[i] == '+' || str[i] == '-')) {
sign = (str[i] == '-') ? -1 : 1;
i++;
}
// 计算数值
while (i < str.length() && isdigit(str[i])) {
res = res * 10 + (str[i] - '0');
if (res * sign > INT_MAX)
return INT_MAX;
if (res * sign < INT_MIN)
return INT_MIN;
i++;
}
return res * sign;
}
int main() {
std::string s = "-12345";
std::cout << "String to Int: " << myAtoi(s) << std::endl;
return 0;
}
Itoa
#include <algorithm>
#include <iostream>
#include <string>
std::string myItoa(int num) {
std::string str = "";
bool isNegative = false;
// 0 的特判
if (num == 0) {
return "0";
}
// 处理负数,转为正数处理
long long n = num;
if (n < 0) {
isNegative = true;
n = -n;
}
// 逆序提取每一位
while (n > 0) {
str += (n % 10 + '0');
n /= 10;
}
// 补上负号
if (isNegative) {
str += '-';
}
// 翻转字符串得到正确顺序
std::reverse(str.begin(), str.end());
return str;
}
int main() {
int n = -12345;
std::cout << "Int to String: " << myItoa(n) << std::endl;
return 0;
}
搜索
DFS
#include <iostream>
#include <vector>
using namespace std;
void dfs(int u, const vector<vector<int>> &graph, vector<bool> &visited) {
visited[u] = true;
for (int neighbor : graph[u]) {
if (!visited[neighbor]) {
dfs(neighbor, graph, visited);
}
}
}
int countConnectedComponents(int n, const vector<vector<int>> &edges) {
vector<vector<int>> graph(n);
// 构建邻接表
for (const auto &edge : edges) {
graph[edge[0]].push_back(edge[1]);
graph[edge[1]].push_back(edge[0]);
}
vector<bool> visited(n, false);
int components = 0;
for (int i = 0; i < n; ++i) {
if (!visited[i]) {
components++;
dfs(i, graph, visited);
}
}
return components;
}
int main() {
int n = 6;
vector<vector<int>> edges = {{0, 1}, {1, 2}, {3, 4}};
cout << "Connection Count: " << countConnectedComponents(n, edges) << endl;
return 0;
}
BFS
#include <iostream>
#include <queue>
#include <vector>
using namespace std;
struct Point {
int x, y, dist;
};
int bfs(vector<vector<int>> &grid, Point start, Point end) {
int rows = grid.size();
int cols = grid[0].size();
vector<vector<bool>> visited(rows, vector<bool>(cols, false));
queue<Point> q;
q.push(start);
visited[start.x][start.y] = true;
// 定义四个方向:上、下、左、右
int dx[] = {-1, 1, 0, 0};
int dy[] = {0, 0, -1, 1};
while (!q.empty()) {
Point curr = q.front();
q.pop();
if (curr.x == end.x && curr.y == end.y) {
return curr.dist;
}
for (int i = 0; i < 4; i++) {
int newX = curr.x + dx[i];
int newY = curr.y + dy[i];
if (newX >= 0 && newX < rows && newY >= 0 && newY < cols &&
grid[newX][newY] == 0 && !visited[newX][newY]) {
visited[newX][newY] = true;
q.push({newX, newY, curr.dist + 1});
}
}
}
return -1; // 无法到达
}
int main() {
// clang-format off
vector<vector<int>> grid = {
{0, 0, 0, 0},
{1, 1, 0, 1},
{0, 0, 0, 0},
{0, 1, 1, 0}
};
// clang-format on
Point start = {0, 0, 0};
Point end = {3, 3, 0};
cout << "Shortest Step: " << bfs(grid, start, end) << endl;
return 0;
}
最小 K 个数
#include <iostream>
#include <queue>
#include <vector>
std::vector<int> getLeastNumbers(const std::vector<int> &arr, int k) {
if (k <= 0 || arr.empty()) {
return {};
}
std::priority_queue<int, std::vector<int>, std::less<int>> max_heap;
// sort
for (int n : arr) {
if (max_heap.size() < k) {
max_heap.push(n);
} else if (n < max_heap.top()) {
max_heap.pop();
max_heap.push(n);
}
}
// copy
std::vector<int> result;
while (!max_heap.empty()) {
result.push_back(max_heap.top());
// result.insert(result.begin(), max_heap.top());
max_heap.pop();
}
return result;
}
int main() {
std::vector<int> arr = {1, 3, 5, 7, 2, 4, 0};
std::vector<int> res = getLeastNumbers(arr, 3);
for (auto i = res.rbegin(); i != res.rend(); i++) {
std::cout << *i << " ";
}
std::cout << std::endl;
return 0;
}
搜索链表相交第一个节点
class ListNode {
val: number;
next: ListNode|null;
constructor(val: number) {
this.val = val;
this.next = null;
}
}
const getIntersectionNode = (headA: ListNode|null, headB: ListNode|null): ListNode|null => {
if (!headA || !headB) return null;
let ptrA: ListNode|null = headA;
let ptrB: ListNode|null = headB;
// 两个指针同时遍历,当指针走到尽头时,跳到另一个链表的头部
while (ptrA !== ptrB) {
ptrA = ptrA === null ? headB : ptrA.next;
ptrB = ptrB === null ? headA : ptrB.next;
}
// 如果没有交点,最终会同时指向 null
return ptrA;
}
// Common List: 8 -> 4 -> 5
const common = new ListNode(8);
common.next = new ListNode(4);
common.next!.next = new ListNode(5);
// ListA: 4 -> 1 -> 8 -> 4 -> 5
const headA = new ListNode(4);
headA.next = new ListNode(1);
headA.next!.next = common;
// ListB: 5 -> 0 -> 1 -> 8 -> 4 -> 5
const headB = new ListNode(5);
headB.next = new ListNode(0);
headB.next!.next = new ListNode(1);
headB.next!.next!.next = common;
const result = getIntersectionNode(headA, headB);
if (result) {
console.log(`First Intersection Node: ${result.val}`);
} else {
console.log('NO INTERSECTION NODE.');
}
#include <iostream>
struct ListNode {
int val;
ListNode *next;
ListNode(int x) : val(x), next(nullptr) {}
};
ListNode *getIntersectionNode(ListNode *headA, ListNode *headB) {
if (!headA || !headB)
return nullptr;
ListNode *ptrA = headA;
ListNode *ptrB = headB;
// 两个指针同时遍历,当指针走到尽头时,跳到另一个链表的头部
while (ptrA != ptrB) {
ptrA = (ptrA == nullptr) ? headB : ptrA->next;
ptrB = (ptrB == nullptr) ? headA : ptrB->next;
}
// 如果没有交点,最终会同时指向 nullptr
return ptrA;
}
int main() {
// Common List: 8 -> 4 -> 5
ListNode *common = new ListNode(8);
common->next = new ListNode(4);
common->next->next = new ListNode(5);
// ListA: 4 -> 1 -> 8 -> 4 -> 5
ListNode *headA = new ListNode(4);
headA->next = new ListNode(1);
headA->next->next = common;
// ListB: 5 -> 0 -> 1 -> 8 -> 4 -> 5
ListNode *headB = new ListNode(5);
headB->next = new ListNode(0);
headB->next->next = new ListNode(1);
headB->next->next->next = common;
ListNode *result = getIntersectionNode(headA, headB);
if (result) {
std::cout << "First Intersection Node: " << result->val << std::endl;
} else {
std::cout << "NO INTERSECTION NODE." << std::endl;
}
return 0;
}
排序
冒泡排序
#include <iostream>
#include <vector>
void bubbleSort(std::vector<int> &arr) {
int n = arr.size();
for (int i = 0; i < n - 1; ++i) {
bool swapped = false; // 优化:记录本轮是否有元素交换
for (int j = 0; j < n - i - 1; ++j) {
if (arr[j] > arr[j + 1]) {
std::swap(arr[j], arr[j + 1]);
swapped = true;
}
}
// 如果某一轮没有发生交换,说明数组已经完全有序,提前退出
if (!swapped) {
break;
}
}
}
int main() {
std::vector<int> data = {8, 3, 1, 7, 0, 10, 2};
bubbleSort(data);
for (int val : data) {
std::cout << val << " ";
}
std::cout << std::endl;
return 0;
}
快速排序(递归版)
function quickSortSimple(arr: number[]): number[] {
if (arr.length <= 1) {
return arr;
}
const pivot = arr[Math.floor(arr.length / 2)];
const left = arr.filter(item => item < pivot);
const middle = arr.filter(item => item === pivot);
const right = arr.filter(item => item > pivot);
return [...quickSortSimple(left), ...middle, ...quickSortSimple(right)];
}
const list = [8, 3, 1, 7, 0, 10, 2];
console.log(quickSortSimple(list));
#include <vector>
#include <iostream>
int partition(std::vector<int> &arr, int low, int high) {
int pivot = arr[low];
while (low < high) {
while (low < high && arr[high] >= pivot) {
high--;
}
arr[low] = arr[high];
while (low < high && arr[low] <= pivot) {
low++;
}
arr[high] = arr[low];
}
arr[low] = pivot;
return low;
}
void quickSort(std::vector<int> &arr, int low, int high) {
if (low < high) {
int pivotIndex = partition(arr, low, high);
quickSort(arr, low, pivotIndex - 1);
quickSort(arr, pivotIndex + 1, high);
}
}
int main() {
std::vector<int> data = {8, 3, 1, 7, 0, 10, 2};
quickSort(data, 0, data.size()-1);
for (const auto &num : data) {
std::cout << num << " ";
}
std::cout << std::endl;
return 0;
}
Leetcode
TwoSum
function twoSum(nums: number[], target: number) : [number, number] {
const map = new Map()
for (let i=0; i<nums.length; i++) {
const c = target - nums[i]
if (map.has(c)) {
return [i, map.get(c)]
}
map.set(nums[i], i);
}
return [0, 0]
}
const ret = twoSum([8, 3, 1, 7, 0, 10, 2], 9)
std::pair<int, int> twoSum(std::vector<int> &nums, int target) {
std::unordered_map<int, int> map;
for (int i = 0; i < nums.size(); i++) {
auto iter = map.find(target - nums[i]);
if (iter != map.end()) {
return {iter->second, i};
}
map.insert(std::pair<int, int>(nums[i], i));
}
return {};
}
int main() {
std::vector<int> nums = {8, 3, 1, 7, 0, 10, 2};
std::pair<int, int> res = twoSum(nums, 9);
std::cout << res.first << "\t" << res.second << std::endl;
return 0;
}
浙公网安备 33010602011771号