mirror of
https://github.com/youngyangyang04/leetcode-master.git
synced 2025-07-07 07:35:35 +08:00
Update
This commit is contained in:
@ -42,7 +42,8 @@
|
|||||||
|
|
||||||
我以[1,2,3]为例,抽象成树形结构如下:
|
我以[1,2,3]为例,抽象成树形结构如下:
|
||||||
|
|
||||||

|
|
||||||
|

|
||||||
|
|
||||||
### 回溯三部曲
|
### 回溯三部曲
|
||||||
|
|
||||||
@ -54,7 +55,7 @@
|
|||||||
|
|
||||||
但排列问题需要一个used数组,标记已经选择的元素,如图橘黄色部分所示:
|
但排列问题需要一个used数组,标记已经选择的元素,如图橘黄色部分所示:
|
||||||
|
|
||||||

|

|
||||||
|
|
||||||
代码如下:
|
代码如下:
|
||||||
|
|
||||||
@ -66,7 +67,7 @@ void backtracking (vector<int>& nums, vector<bool>& used)
|
|||||||
|
|
||||||
* 递归终止条件
|
* 递归终止条件
|
||||||
|
|
||||||

|

|
||||||
|
|
||||||
可以看出叶子节点,就是收割结果的地方。
|
可以看出叶子节点,就是收割结果的地方。
|
||||||
|
|
||||||
|
@ -134,17 +134,17 @@ x = (target + sum) / 2
|
|||||||
|
|
||||||
大家看到(target + sum) / 2 应该担心计算的过程中向下取整有没有影响。
|
大家看到(target + sum) / 2 应该担心计算的过程中向下取整有没有影响。
|
||||||
|
|
||||||
这么担心就对了,例如sum 是5,S是2的话其实就是无解的,所以:
|
这么担心就对了,例如sum是5,target是2 的话其实就是无解的,所以:
|
||||||
|
|
||||||
```CPP
|
```CPP
|
||||||
(C++代码中,输入的S 就是题目描述的 target)
|
(C++代码中,输入的S 就是题目描述的 target)
|
||||||
if ((S + sum) % 2 == 1) return 0; // 此时没有方案
|
if ((target + sum) % 2 == 1) return 0; // 此时没有方案
|
||||||
```
|
```
|
||||||
|
|
||||||
同时如果 S的绝对值已经大于sum,那么也是没有方案的。
|
同时如果target 的绝对值已经大于sum,那么也是没有方案的。
|
||||||
|
|
||||||
```CPP
|
```CPP
|
||||||
(C++代码中,输入的S 就是题目描述的 target)
|
if (abs(target) > sum) return 0; // 此时没有方案
|
||||||
if (abs(S) > sum) return 0; // 此时没有方案
|
|
||||||
```
|
```
|
||||||
|
|
||||||
再回归到01背包问题,为什么是01背包呢?
|
再回归到01背包问题,为什么是01背包呢?
|
||||||
@ -213,9 +213,9 @@ dp[j]其他下标对应的数值也应该初始化为0,从递推公式也可
|
|||||||
|
|
||||||
5. 举例推导dp数组
|
5. 举例推导dp数组
|
||||||
|
|
||||||
输入:nums: [1, 1, 1, 1, 1], S: 3
|
输入:nums: [1, 1, 1, 1, 1], target: 3
|
||||||
|
|
||||||
bagSize = (S + sum) / 2 = (3 + 5) / 2 = 4
|
bagSize = (target + sum) / 2 = (3 + 5) / 2 = 4
|
||||||
|
|
||||||
dp数组状态变化如下:
|
dp数组状态变化如下:
|
||||||
|
|
||||||
@ -226,12 +226,12 @@ C++代码如下:
|
|||||||
```CPP
|
```CPP
|
||||||
class Solution {
|
class Solution {
|
||||||
public:
|
public:
|
||||||
int findTargetSumWays(vector<int>& nums, int S) {
|
int findTargetSumWays(vector<int>& nums, int target) {
|
||||||
int sum = 0;
|
int sum = 0;
|
||||||
for (int i = 0; i < nums.size(); i++) sum += nums[i];
|
for (int i = 0; i < nums.size(); i++) sum += nums[i];
|
||||||
if (abs(S) > sum) return 0; // 此时没有方案
|
if (abs(target) > sum) return 0; // 此时没有方案
|
||||||
if ((S + sum) % 2 == 1) return 0; // 此时没有方案
|
if ((target + sum) % 2 == 1) return 0; // 此时没有方案
|
||||||
int bagSize = (S + sum) / 2;
|
int bagSize = (target + sum) / 2;
|
||||||
vector<int> dp(bagSize + 1, 0);
|
vector<int> dp(bagSize + 1, 0);
|
||||||
dp[0] = 1;
|
dp[0] = 1;
|
||||||
for (int i = 0; i < nums.size(); i++) {
|
for (int i = 0; i < nums.size(); i++) {
|
||||||
@ -655,3 +655,52 @@ public class Solution
|
|||||||
<a href="https://programmercarl.com/other/kstar.html" target="_blank">
|
<a href="https://programmercarl.com/other/kstar.html" target="_blank">
|
||||||
<img src="../pics/网站星球宣传海报.jpg" width="1000"/>
|
<img src="../pics/网站星球宣传海报.jpg" width="1000"/>
|
||||||
</a>
|
</a>
|
||||||
|
|
||||||
|
|
||||||
|
class Solution {
|
||||||
|
public:
|
||||||
|
int findTargetSumWays(vector<int>& nums, int target) {
|
||||||
|
int sum = 0;
|
||||||
|
for (int i = 0; i < nums.size(); i++) sum += nums[i];
|
||||||
|
if (abs(target) > sum) return 0; // 此时没有方案
|
||||||
|
if ((target + sum) % 2 == 1) return 0; // 此时没有方案
|
||||||
|
int bagSize = (target + sum) / 2;
|
||||||
|
|
||||||
|
vector<vector<int>> dp(nums.size(), vector<int>(bagSize + 1, 0));
|
||||||
|
|
||||||
|
if (nums[0] <= bagSize) dp[0][nums[0]] = 1;
|
||||||
|
|
||||||
|
dp[0][0] = 1;
|
||||||
|
|
||||||
|
int numZero = 0;
|
||||||
|
for (int i = 0; i < nums.size(); i++) {
|
||||||
|
if (nums[i] == 0) numZero++;
|
||||||
|
dp[i][0] = (int) pow(2.0, numZero);
|
||||||
|
}
|
||||||
|
|
||||||
|
for (int i = 1; i < nums.size(); i++) {
|
||||||
|
for (int j = 0; j <= bagSize; j++) {
|
||||||
|
if (nums[i] > j) dp[i][j] = dp[i - 1][j];
|
||||||
|
else dp[i][j] = dp[i - 1][j] + dp[i - 1][j - nums[i]];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
for (int i = 0; i < nums.size(); i++) {
|
||||||
|
for (int j = 0; j <= bagSize; j++) {
|
||||||
|
cout << dp[i][j] << " ";
|
||||||
|
}
|
||||||
|
cout << endl;
|
||||||
|
}
|
||||||
|
return dp[nums.size() - 1][bagSize];
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
1 1 0 0 0
|
||||||
|
1 2 1 0 0
|
||||||
|
1 3 3 1 0
|
||||||
|
1 4 6 4 1
|
||||||
|
1 5 10 10 5
|
||||||
|
|
||||||
|
初始化 如果没有0, dp[i][0] = 1; 即所有元素都不取。
|
||||||
|
|
||||||
|
用元素 取与不取来举例
|
||||||
|
|
||||||
|
@ -64,7 +64,7 @@
|
|||||||
|
|
||||||

|

|
||||||
|
|
||||||
本图中,对所有边进行松弛,真正有效的松弛,只有松弛 边(节点1->节点2) 和 边(节点1->节点5) 。
|
本图中,对所有边进行松弛,真正有效的松弛,只有松弛 边(节点1->节点2) 和 边(节点1->节点3) 。
|
||||||
|
|
||||||
而松弛 边(节点4->节点6) ,边(节点5->节点3)等等 都是无效的操作,因为 节点4 和 节点 5 都是没有被计算过的节点。
|
而松弛 边(节点4->节点6) ,边(节点5->节点3)等等 都是无效的操作,因为 节点4 和 节点 5 都是没有被计算过的节点。
|
||||||
|
|
||||||
|
127
problems/kamacoder/0151.手机流畅运行的秘密.md
Normal file
127
problems/kamacoder/0151.手机流畅运行的秘密.md
Normal file
@ -0,0 +1,127 @@
|
|||||||
|
# 151. 手机流畅运行的秘密
|
||||||
|
|
||||||
|
[题目链接](https://kamacoder.com/problempage.php?pid=1229)
|
||||||
|
|
||||||
|
先运行 能留下电量多的 任务,才能有余电运行其他任务。
|
||||||
|
|
||||||
|
任务1,1:10 ,运行完 能留下 9个电
|
||||||
|
|
||||||
|
任务2,2:12,运行完 能留下 10个电
|
||||||
|
|
||||||
|
任务3,3:10,运行完 能留下 7个电。
|
||||||
|
|
||||||
|
运行顺序: 任务2 -> 任务1 -> 任务3
|
||||||
|
|
||||||
|
按照 最低初始电量 - 耗电量,从大到小排序。
|
||||||
|
|
||||||
|
计算总电量,需要 从小到大 遍历, 不断取 总电量 + 任务耗电量 与 任务最低初始电量 的最大值。
|
||||||
|
|
||||||
|
```CPP
|
||||||
|
#include<bits/stdc++.h>
|
||||||
|
using namespace std;
|
||||||
|
|
||||||
|
bool cmp(const pair<int,int>& taskA, const pair<int,int>& taskB) {
|
||||||
|
return (taskA.second - taskA.first) < (taskB.second - taskB.first);
|
||||||
|
}
|
||||||
|
int main() {
|
||||||
|
string str, tmp;
|
||||||
|
vector<pair<int,int>> tasks;
|
||||||
|
|
||||||
|
//处理输入
|
||||||
|
getline(cin, str);
|
||||||
|
stringstream ss(str);
|
||||||
|
while (getline(ss, tmp, ',')) {
|
||||||
|
int p = tmp.find(":");
|
||||||
|
string a = tmp.substr(0, p);
|
||||||
|
string b = tmp.substr(p + 1);
|
||||||
|
tasks.push_back({stoi(a), stoi(b)});
|
||||||
|
}
|
||||||
|
|
||||||
|
// 按照差值从小到大排序
|
||||||
|
sort(tasks.begin(), tasks.end(), cmp);
|
||||||
|
|
||||||
|
// 收集结果
|
||||||
|
int result = 0;
|
||||||
|
for (int i = 0 ; i < tasks.size(); i++) {
|
||||||
|
result = max(result + tasks[i].first, tasks[i].second);
|
||||||
|
}
|
||||||
|
|
||||||
|
result = result <= 4800 ? result : -1;
|
||||||
|
cout << result << endl;
|
||||||
|
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
Java版本:
|
||||||
|
|
||||||
|
```Java
|
||||||
|
import java.util.*;
|
||||||
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
|
public class Main {
|
||||||
|
public static void main(String[] args) {
|
||||||
|
Scanner sc = new Scanner(System.in);
|
||||||
|
String str = sc.nextLine();
|
||||||
|
String[] tasksArray = str.split(",");
|
||||||
|
List<Pair> tasks = Arrays.stream(tasksArray)
|
||||||
|
.map(task -> {
|
||||||
|
String[] parts = task.split(":");
|
||||||
|
return new Pair(Integer.parseInt(parts[0]), Integer.parseInt(parts[1]));
|
||||||
|
})
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
|
||||||
|
// 按照差值从小到大排序
|
||||||
|
Collections.sort(tasks, (taskA, taskB) ->
|
||||||
|
(taskA.second - taskA.first) - (taskB.second - taskB.first)
|
||||||
|
);
|
||||||
|
|
||||||
|
// 收集结果
|
||||||
|
int result = 0;
|
||||||
|
for (Pair task : tasks) {
|
||||||
|
result = Math.max(result + task.first, task.second);
|
||||||
|
}
|
||||||
|
|
||||||
|
result = result <= 4800 ? result : -1;
|
||||||
|
System.out.println(result);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class Pair {
|
||||||
|
int first;
|
||||||
|
int second;
|
||||||
|
|
||||||
|
Pair(int first, int second) {
|
||||||
|
this.first = first;
|
||||||
|
this.second = second;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
```
|
||||||
|
|
||||||
|
Python版本:
|
||||||
|
|
||||||
|
```python
|
||||||
|
def main():
|
||||||
|
import sys
|
||||||
|
input = sys.stdin.read
|
||||||
|
|
||||||
|
str = input().strip()
|
||||||
|
tasks = []
|
||||||
|
for tmp in str.split(','):
|
||||||
|
a, b = map(int, tmp.split(':'))
|
||||||
|
tasks.append((a, b))
|
||||||
|
|
||||||
|
# 按照差值从小到大排序
|
||||||
|
tasks.sort(key=lambda task: task[1] - task[0])
|
||||||
|
|
||||||
|
# 收集结果
|
||||||
|
result = 0
|
||||||
|
for task in tasks:
|
||||||
|
result = max(result + task[0], task[1])
|
||||||
|
|
||||||
|
result = result if result <= 4800 else -1
|
||||||
|
print(result)
|
||||||
|
|
||||||
|
if __name__ == "__main__":
|
||||||
|
main()
|
||||||
|
```
|
121
problems/kamacoder/0152.小米手机通信校准.md
Normal file
121
problems/kamacoder/0152.小米手机通信校准.md
Normal file
@ -0,0 +1,121 @@
|
|||||||
|
|
||||||
|
|
||||||
|
# 152. 小米手机通信校准
|
||||||
|
|
||||||
|
[题目链接](https://kamacoder.com/problempage.php?pid=1230)
|
||||||
|
|
||||||
|
一道模拟题,但比较考察 代码能力。
|
||||||
|
|
||||||
|
遍历去找 里 freq 最近的 freg就好, 需要记录刚遍历过的的freg和 loss,因为可能有 相邻一样的 freg。
|
||||||
|
|
||||||
|
```CPP
|
||||||
|
#include <bits/stdc++.h>
|
||||||
|
using namespace std;
|
||||||
|
|
||||||
|
int main() {
|
||||||
|
int freq;
|
||||||
|
cin >> freq;
|
||||||
|
string data;
|
||||||
|
double result = 0;
|
||||||
|
int last_freg = 0; // 记录上一个 freg
|
||||||
|
int last_loss = 0; // 记录上一个loss
|
||||||
|
while(cin >> data) {
|
||||||
|
int index = data.find(':');
|
||||||
|
int freg = stoi(data.substr(0, index)); // 获取 freg 和 loss
|
||||||
|
int loss = stoi(data.substr(index + 1));
|
||||||
|
// 两遍一样
|
||||||
|
if(abs(freg - freq) == abs(last_freg - freq)) {
|
||||||
|
result = (double)(last_loss + loss)/2.0;
|
||||||
|
} // 否则更新最新的result
|
||||||
|
else if(abs(freg - freq) < abs(last_freg - freq)){
|
||||||
|
result = (double)loss;
|
||||||
|
}
|
||||||
|
last_freg = freg;
|
||||||
|
last_loss = loss;
|
||||||
|
}
|
||||||
|
printf("%.1lf\n", result);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
```
|
||||||
|
|
||||||
|
Java 版本:
|
||||||
|
|
||||||
|
```Java
|
||||||
|
|
||||||
|
import java.util.Scanner;
|
||||||
|
|
||||||
|
public class Main {
|
||||||
|
public static void main(String[] args) {
|
||||||
|
Scanner sc = new Scanner(System.in);
|
||||||
|
int freq = sc.nextInt();
|
||||||
|
sc.nextLine(); // 读取换行符
|
||||||
|
|
||||||
|
String inputLine = sc.nextLine(); // 读取包含所有后续输入的行
|
||||||
|
String[] data = inputLine.split(" "); // 根据空格分割输入
|
||||||
|
|
||||||
|
double result = 0;
|
||||||
|
int lastFreq = 0; // 记录上一个 freg
|
||||||
|
int lastLoss = 0; // 记录上一个 loss
|
||||||
|
|
||||||
|
for (String entry : data) {
|
||||||
|
int index = entry.indexOf(':');
|
||||||
|
int freg = Integer.parseInt(entry.substring(0, index)); // 获取 freg 和 loss
|
||||||
|
int loss = Integer.parseInt(entry.substring(index + 1));
|
||||||
|
|
||||||
|
// 两遍一样
|
||||||
|
if (Math.abs(freg - freq) == Math.abs(lastFreq - freq)) {
|
||||||
|
result = (double) (lastLoss + loss) / 2.0;
|
||||||
|
}
|
||||||
|
// 否则更新最新的 result
|
||||||
|
else if (Math.abs(freg - freq) < Math.abs(lastFreq - freq)) {
|
||||||
|
result = (double) loss;
|
||||||
|
}
|
||||||
|
|
||||||
|
lastFreq = freg;
|
||||||
|
lastLoss = loss;
|
||||||
|
}
|
||||||
|
|
||||||
|
System.out.printf("%.1f\n", result);
|
||||||
|
sc.close();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
```
|
||||||
|
|
||||||
|
Python版本:
|
||||||
|
|
||||||
|
```python
|
||||||
|
def main():
|
||||||
|
import sys
|
||||||
|
input = sys.stdin.read
|
||||||
|
data = input().split()
|
||||||
|
|
||||||
|
freq = int(data[0])
|
||||||
|
result = 0
|
||||||
|
last_freg = 0 # 记录上一个 freg
|
||||||
|
last_loss = 0 # 记录上一个 loss
|
||||||
|
|
||||||
|
for i in range(1, len(data)):
|
||||||
|
item = data[i]
|
||||||
|
index = item.find(':')
|
||||||
|
freg = int(item[:index]) # 获取 freg 和 loss
|
||||||
|
loss = int(item[index + 1:])
|
||||||
|
|
||||||
|
# 两遍一样
|
||||||
|
if abs(freg - freq) == abs(last_freg - freq):
|
||||||
|
result = (last_loss + loss) / 2.0
|
||||||
|
# 否则更新最新的 result
|
||||||
|
elif abs(freg - freq) < abs(last_freg - freq):
|
||||||
|
result = loss
|
||||||
|
|
||||||
|
last_freg = freg
|
||||||
|
last_loss = loss
|
||||||
|
|
||||||
|
print(f"{result:.1f}")
|
||||||
|
|
||||||
|
if __name__ == "__main__":
|
||||||
|
main()
|
||||||
|
|
||||||
|
|
||||||
|
```
|
Reference in New Issue
Block a user