Skip to content

Commit e60e71f

Browse files
committed
add 2684
1 parent d472c68 commit e60e71f

File tree

8 files changed

+406
-52
lines changed

8 files changed

+406
-52
lines changed

src/.vuepress/sidebar.ts

+1
Original file line numberDiff line numberDiff line change
@@ -567,6 +567,7 @@ export default sidebar({
567567
"2675",
568568
"2676",
569569
"2677",
570+
"2684",
570571
"2694",
571572
"2695",
572573
"2696"

src/plan/contest_list.md

+1-1
Original file line numberDiff line numberDiff line change
@@ -1357,7 +1357,7 @@ headerDepth: 0
13571357
| :------: | :------ | :------: | :------ | :------ |
13581358
| 2682 | [找出转圈游戏输家](https://leetcode.com/problems/find-the-losers-of-the-circular-game) | | [`数组`](/tag/array.md) [`哈希表`](/tag/hash-table.md) [`模拟`](/tag/simulation.md) | <font color=#15bd66>Easy</font> |
13591359
| 2683 | [相邻值的按位异或](https://leetcode.com/problems/neighboring-bitwise-xor) | | [`位运算`](/tag/bit-manipulation.md) [`数组`](/tag/array.md) | <font color=#ffb800>Medium</font> |
1360-
| 2684 | [矩阵中移动的最大次数](https://leetcode.com/problems/maximum-number-of-moves-in-a-grid) | | [`数组`](/tag/array.md) [`动态规划`](/tag/dynamic-programming.md) [`矩阵`](/tag/matrix.md) | <font color=#ffb800>Medium</font> |
1360+
| 2684 | [矩阵中移动的最大次数](https://leetcode.com/problems/maximum-number-of-moves-in-a-grid) | [[✓]](/problem/2684.md) | [`数组`](/tag/array.md) [`动态规划`](/tag/dynamic-programming.md) [`矩阵`](/tag/matrix.md) | <font color=#ffb800>Medium</font> |
13611361
| 2685 | [统计完全连通分量的数量](https://leetcode.com/problems/count-the-number-of-complete-components) | | [`深度优先搜索`](/tag/depth-first-search.md) [`广度优先搜索`](/tag/breadth-first-search.md) [`图`](/tag/graph.md) | <font color=#ffb800>Medium</font> |
13621362

13631363

src/problem/2632.md

+168-47
Original file line numberDiff line numberDiff line change
@@ -4,57 +4,178 @@
44

55
## 题目
66

7+
Given a function `fn`, return a **curried** version of that function.
8+
9+
A **curried** function is a function that accepts fewer or an equal number of parameters as the original function and returns either another **curried** function or the same value the original function would have returned.
10+
11+
In practical terms, if you called the original function like `sum(1,2,3)`, you would call the **curried** version like `csum(1)(2)(3)`, `csum(1)(2,3) `, `csum(1,2)(3)`, or `csum(1,2,3)`. All these methods of calling the **curried** function should return the same value as the original.
12+
13+
**Example 1:**
14+
15+
> Input:
16+
>
17+
> fn = function sum(a, b, c) { return a + b + c; }
18+
>
19+
> inputs = [[1],[2],[3]]
20+
>
21+
> Output: 6
22+
>
23+
> Explanation:
24+
>
25+
> The code being executed is:
26+
>
27+
> const curriedSum = curry(fn);
28+
>
29+
> curriedSum(1)(2)(3) === 6;
30+
>
31+
> curriedSum(1)(2)(3) should return the same value as sum(1, 2, 3).
32+
33+
**Example 2:**
34+
35+
> Input:
36+
>
37+
> fn = function sum(a, b, c) { return a + b + c; }
38+
>
39+
> inputs = [[1,2],[3]]
40+
>
41+
> Output: 6
42+
>
43+
> Explanation:
44+
>
45+
> curriedSum(1, 2)(3) should return the same value as sum(1, 2, 3).
46+
47+
**Example 3:**
48+
49+
> Input:
50+
>
51+
> fn = function sum(a, b, c) { return a + b + c; }
52+
>
53+
> inputs = [[],[],[1,2,3]]
54+
>
55+
> Output: 6
56+
>
57+
> Explanation:
58+
>
59+
> You should be able to pass the parameters in any way, including all at once or none at all.
60+
>
61+
> curriedSum()()(1, 2, 3) should return the same value as sum(1, 2, 3).
62+
63+
**Example 4:**
64+
65+
> Input:
66+
>
67+
> fn = function life() { return 42; }
68+
>
69+
> inputs = [[]]
70+
>
71+
> Output: 42
72+
>
73+
> Explanation:
74+
>
75+
> currying a function that accepts zero parameters should effectively do nothing.
76+
>
77+
> curriedLife() === 42
78+
79+
**Constraints:**
80+
81+
- `1 <= inputs.length <= 1000`
82+
- `0 <= inputs[i][j] <= 10^5`
83+
- `0 <= fn.length <= 1000`
84+
- `inputs.flat().length == fn.length`
85+
- function parameters explicitly defined
86+
- If `fn.length > 0` then the last array in `inputs` is not empty
87+
- If `fn.length === 0` then `inputs.length === 1`
88+
89+
## 题目大意
90+
91+
请你编写一个函数,它接收一个其他的函数,并返回该函数的 **柯里化** 后的形式。
92+
93+
**柯里化** 函数的定义是接受与原函数相同数量或更少数量的参数,并返回另一个 **柯里化** 后的函数或与原函数相同的值。
94+
95+
实际上,当你调用原函数,如 `sum(1,2,3)` 时,它将调用 **柯里化** 函数的某个形式,如 `csum(1)(2)(3)`
96+
`csum(1)(2,3)``csum(1,2)(3)`,或 `csum(1,2,3)` 。所有调用 **柯里化** 函数的方法都应该返回与原始函数相同的值。
97+
98+
**示例 1:**
99+
100+
> **输入:**
101+
>
102+
> fn = function sum(a, b, c) { return a + b + c; }
103+
>
104+
> inputs = [[1],[2],[3]]
105+
>
106+
> **输出:** 6
107+
>
108+
> **解释:**
109+
>
110+
> 执行的代码是:
111+
>
112+
> const curriedSum = curry(fn);
113+
>
114+
> curriedSum(1)(2)(3) === 6;
115+
>
116+
> curriedSum(1)(2)(3) 应该返回像原函数 sum(1, 2, 3) 一样的值。
117+
118+
**示例 2:**
119+
120+
> **输入:**
121+
>
122+
> fn = function sum(a, b, c) { return a + b + c; }
123+
>
124+
> inputs = [[1,2],[3]]
125+
>
126+
> **输出:** 6
127+
>
128+
> **解释:**
129+
>
130+
> curriedSum(1, 2)(3) 应该返回像原函数 sum(1, 2, 3) 一样的值。
131+
132+
**示例 3:**
133+
134+
> **输入:**
135+
>
136+
> fn = function sum(a, b, c) { return a + b + c; }
137+
>
138+
> inputs = [[],[],[1,2,3]]
139+
>
140+
> **输出:** 6
141+
>
142+
> **解释:**
143+
>
144+
> 你应该能够以任何方式传递参数,包括一次性传递所有参数或完全不传递参数。
145+
>
146+
> curriedSum()()(1, 2, 3) 应该返回像原函数 sum(1, 2, 3) 一样的值。
147+
148+
**示例 4:**
149+
150+
> **输入:**
151+
>
152+
> fn = function life() { return 42; }
153+
>
154+
> inputs = [[]]
155+
>
156+
> **输出:** 42
157+
>
158+
> **解释:**
159+
>
160+
> 柯里化一个没有接收参数,没做有效操作的函数。
161+
>
162+
> curriedLife() === 42
163+
164+
**提示:**
165+
166+
- `1 <= inputs.length <= 1000`
167+
- `0 <= inputs[i][j] <= 10^5`
168+
- `0 <= fn.length <= 1000`
169+
- `inputs.flat().length == fn.length`
170+
- `函数参数需要被显式定义`
171+
- 如果 `fn.length > 0` 则最后一个数组 `inputs` 不为空
172+
- 如果 `fn.length === 0``inputs.length === 1`
173+
7174
## 解题思路
8175

9176
[柯里化(Currying)](https://en.wikipedia.org/wiki/Currying)是一种关于函数的高阶技术,它是指将一个函数从可调用的 `f(a, b, c)` 转换为可调用的 `f(a)(b)(c)`。柯里化不会调用函数,只是对函数进行转换。
10177

11-
#### 柯里化的目的是什么?
12-
13-
可以从一个实际中的例子中,了解柯里化的好处。
14-
15-
例如,有一个用于格式化和输出信息的日志(logging)函数 `log(date, importance, message)`
16-
17-
```js
18-
function log(date, importance, message) {
19-
alert(`[${date.getHours()}:${date.getMinutes()}] [${importance}] ${message}`);
20-
}
21-
```
22-
23-
将它柯里化:
24-
25-
`log = _.curry(log);`
26-
27-
柯里化之后,`log` 仍正常运行:
28-
29-
`log(new Date(), "DEBUG", "some debug"); // log(a, b, c)`
30-
31-
但是也能以柯里化形式运行:
32-
33-
`log(new Date())("DEBUG")("some debug"); // log(a)(b)(c)`
34-
35-
现在,可以轻松地为当前日志创建便捷函数:
36-
37-
```js
38-
// logNow 会是带有固定第一个参数的日志的部分应用函数
39-
let logNow = log(new Date());
40-
41-
// 使用它
42-
logNow('INFO', 'message'); // [HH:mm] INFO message
43-
```
44-
45-
现在,`logNow` 是具有固定第一个参数的 `log`,换句话说,就是更简短的“部分应用函数(partially applied function)”或“部分函数(partial)”。
46-
47-
可以更进一步,为当前的调试日志(debug log)提供便捷函数:
48-
49-
```js
50-
let debugNow = logNow('DEBUG');
51-
52-
debugNow('message'); // [HH:mm] DEBUG message
53-
```
54-
55-
因此,柯里化让我们能够更容易地获取部分应用函数。就像在日志记录示例中看到的那样,普通函数 `log(date, importance, message)` 在被柯里化之后,当调用它的时候传入一个参数(如 `log(date)`)或两个参数(`log(date, importance)`)时,它会返回部分应用函数。
56-
57-
#### 实现柯里化函数的思路
178+
实现柯里化函数的思路如下:
58179

59180
1. **函数参数处理**
60181

0 commit comments

Comments
 (0)