Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit 6f0e93c

Browse files
Merge branch 'master' into 0232
2 parents 8d3e5b4 + d69eab3 commit 6f0e93c

File tree

180 files changed

+5490
-419
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

180 files changed

+5490
-419
lines changed

‎problems/0001.两数之和.md

Lines changed: 44 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77

88
## 1. 两数之和
99

10-
[力扣题目链接](https://leetcode-cn.com/problems/two-sum/)
10+
[力扣题目链接](https://leetcode.cn/problems/two-sum/)
1111

1212
给定一个整数数组 nums 和一个目标值 target,请你在该数组中找出和为目标值的那 两个 整数,并返回他们的数组下标。
1313

@@ -275,5 +275,48 @@ class Solution {
275275
}
276276
```
277277

278+
Scala:
279+
```scala
280+
object Solution {
281+
// 导入包
282+
import scala.collection.mutable
283+
def twoSum(nums: Array[Int], target: Int): Array[Int] = {
284+
// key存储值,value存储下标
285+
val map = new mutable.HashMap[Int, Int]()
286+
for (i <- nums.indices) {
287+
val tmp = target - nums(i) // 计算差值
288+
// 如果这个差值存在于map,则说明找到了结果
289+
if (map.contains(tmp)) {
290+
return Array(map.get(tmp).get, i)
291+
}
292+
// 如果不包含把当前值与其下标放到map
293+
map.put(nums(i), i)
294+
}
295+
// 如果没有找到直接返回一个空的数组,return关键字可以省略
296+
new Array[Int](2)
297+
}
298+
}
299+
```
300+
301+
C#:
302+
```csharp
303+
public class Solution {
304+
public int[] TwoSum(int[] nums, int target) {
305+
Dictionary<int ,int> dic= new Dictionary<int,int>();
306+
for(int i=0;i<nums.Length;i++){
307+
int imp= target-nums[i];
308+
if(dic.ContainsKey(imp)&&dic[imp]!=i){
309+
return new int[]{i, dic[imp]};
310+
}
311+
if(!dic.ContainsKey(nums[i])){
312+
dic.Add(nums[i],i);
313+
}
314+
}
315+
return new int[]{0, 0};
316+
}
317+
}
318+
```
319+
320+
278321
-----------------------
279322
<div align="center"><img src=https://code-thinking.cdn.bcebos.com/pics/01二维码一.jpg width=500> </img></div>

‎problems/0005.最长回文子串.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88

99
# 5.最长回文子串
1010

11-
[力扣题目链接](https://leetcode-cn.com/problems/longest-palindromic-substring/)
11+
[力扣题目链接](https://leetcode.cn/problems/longest-palindromic-substring/)
1212

1313
给你一个字符串 s,找到 s 中最长的回文子串。
1414

‎problems/0015.三数之和.md

Lines changed: 115 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@
1010
1111
# 第15题. 三数之和
1212

13-
[力扣题目链接](https://leetcode-cn.com/problems/3sum/)
13+
[力扣题目链接](https://leetcode.cn/problems/3sum/)
1414

1515
给你一个包含 n 个整数的数组 nums,判断 nums 中是否存在三个元素 a,b,c ,使得 a + b + c = 0 ?请你找出所有满足条件且不重复的三元组。
1616

@@ -345,6 +345,76 @@ var threeSum = function(nums) {
345345
return res
346346
};
347347
```
348+
349+
解法二:nSum通用解法。递归
350+
351+
```js
352+
/**
353+
* nsum通用解法,支持2sum,3sum,4sum...等等
354+
* 时间复杂度分析:
355+
* 1. n = 2时,时间复杂度O(NlogN),排序所消耗的时间。、
356+
* 2. n > 2时,时间复杂度为O(N^n-1),即N的n-1次方,至少是2次方,此时可省略排序所消耗的时间。举例:3sum为O(n^2),4sum为O(n^3)
357+
* @param {number[]} nums
358+
* @return {number[][]}
359+
*/
360+
var threeSum = function (nums) {
361+
// nsum通用解法核心方法
362+
function nSumTarget(nums, n, start, target) {
363+
// 前提:nums要先排序好
364+
let res = [];
365+
if (n === 2) {
366+
res = towSumTarget(nums, start, target);
367+
} else {
368+
for (let i = start; i < nums.length; i++) {
369+
// 递归求(n - 1)sum
370+
let subRes = nSumTarget(
371+
nums,
372+
n - 1,
373+
i + 1,
374+
target - nums[i]
375+
);
376+
for (let j = 0; j < subRes.length; j++) {
377+
res.push([nums[i], ...subRes[j]]);
378+
}
379+
// 跳过相同元素
380+
while (nums[i] === nums[i + 1]) i++;
381+
}
382+
}
383+
return res;
384+
}
385+
386+
function towSumTarget(nums, start, target) {
387+
// 前提:nums要先排序好
388+
let res = [];
389+
let len = nums.length;
390+
let left = start;
391+
let right = len - 1;
392+
while (left < right) {
393+
let sum = nums[left] + nums[right];
394+
if (sum < target) {
395+
while (nums[left] === nums[left + 1]) left++;
396+
left++;
397+
} else if (sum > target) {
398+
while (nums[right] === nums[right - 1]) right--;
399+
right--;
400+
} else {
401+
// 相等
402+
res.push([nums[left], nums[right]]);
403+
// 跳过相同元素
404+
while (nums[left] === nums[left + 1]) left++;
405+
while (nums[right] === nums[right - 1]) right--;
406+
left++;
407+
right--;
408+
}
409+
}
410+
return res;
411+
}
412+
nums.sort((a, b) => a - b);
413+
// n = 3,此时求3sum之和
414+
return nSumTarget(nums, 3, 0, 0);
415+
};
416+
```
417+
348418
TypeScript:
349419

350420
```typescript
@@ -616,6 +686,49 @@ public class Solution
616686
}
617687
}
618688
```
619-
689+
Scala:
690+
```scala
691+
object Solution {
692+
// 导包
693+
import scala.collection.mutable.ListBuffer
694+
import scala.util.control.Breaks.{break, breakable}
695+
696+
def threeSum(nums: Array[Int]): List[List[Int]] = {
697+
// 定义结果集,最后需要转换为List
698+
val res = ListBuffer[List[Int]]()
699+
val nums_tmp = nums.sorted // 对nums进行排序
700+
for (i <- nums_tmp.indices) {
701+
// 如果要排的第一个数字大于0,直接返回结果
702+
if (nums_tmp(i) > 0) {
703+
return res.toList
704+
}
705+
// 如果i大于0并且和前一个数字重复,则跳过本次循环,相当于continue
706+
breakable {
707+
if (i > 0 && nums_tmp(i) == nums_tmp(i - 1)) {
708+
break
709+
} else {
710+
var left = i + 1
711+
var right = nums_tmp.length - 1
712+
while (left < right) {
713+
var sum = nums_tmp(i) + nums_tmp(left) + nums_tmp(right) // 求三数之和
714+
if (sum < 0) left += 1
715+
else if (sum > 0) right -= 1
716+
else {
717+
res += List(nums_tmp(i), nums_tmp(left), nums_tmp(right)) // 如果等于0 添加进结果集
718+
// 为了避免重复,对left和right进行移动
719+
while (left < right && nums_tmp(left) == nums_tmp(left + 1)) left += 1
720+
while (left < right && nums_tmp(right) == nums_tmp(right - 1)) right -= 1
721+
left += 1
722+
right -= 1
723+
}
724+
}
725+
}
726+
}
727+
}
728+
// 最终返回需要转换为List,return关键字可以省略
729+
res.toList
730+
}
731+
}
732+
```
620733
-----------------------
621734
<div align="center"><img src=https://code-thinking.cdn.bcebos.com/pics/01二维码一.jpg width=500> </img></div>

‎problems/0017.电话号码的字母组合.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77

88
# 17.电话号码的字母组合
99

10-
[力扣题目链接](https://leetcode-cn.com/problems/letter-combinations-of-a-phone-number/)
10+
[力扣题目链接](https://leetcode.cn/problems/letter-combinations-of-a-phone-number/)
1111

1212
给定一个仅包含数字 2-9 的字符串,返回所有它能表示的字母组合。
1313

‎problems/0018.四数之和.md

Lines changed: 45 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@
1010
1111
# 第18题. 四数之和
1212

13-
[力扣题目链接](https://leetcode-cn.com/problems/4sum/)
13+
[力扣题目链接](https://leetcode.cn/problems/4sum/)
1414

1515
题意:给定一个包含 n 个整数的数组 nums 和一个目标值 target,判断 nums 中是否存在四个元素 a,b,c 和 d ,使得 a + b + c + d 的值与 target 相等?找出所有满足条件且不重复的四元组。
1616

@@ -522,6 +522,49 @@ public class Solution
522522
}
523523
}
524524
```
525-
525+
Scala:
526+
```scala
527+
object Solution {
528+
// 导包
529+
import scala.collection.mutable.ListBuffer
530+
import scala.util.control.Breaks.{break, breakable}
531+
def fourSum(nums: Array[Int], target: Int): List[List[Int]] = {
532+
val res = ListBuffer[List[Int]]()
533+
val nums_tmp = nums.sorted // 先排序
534+
for (i <- nums_tmp.indices) {
535+
breakable {
536+
if (i > 0 && nums_tmp(i) == nums_tmp(i - 1)) {
537+
break // 如果该值和上次的值相同,跳过本次循环,相当于continue
538+
} else {
539+
for (j <- i + 1 until nums_tmp.length) {
540+
breakable {
541+
if (j > i + 1 && nums_tmp(j) == nums_tmp(j - 1)) {
542+
break // 同上
543+
} else {
544+
// 双指针
545+
var (left, right) = (j + 1, nums_tmp.length - 1)
546+
while (left < right) {
547+
var sum = nums_tmp(i) + nums_tmp(j) + nums_tmp(left) + nums_tmp(right)
548+
if (sum == target) {
549+
// 满足要求,直接加入到集合里面去
550+
res += List(nums_tmp(i), nums_tmp(j), nums_tmp(left), nums_tmp(right))
551+
while (left < right && nums_tmp(left) == nums_tmp(left + 1)) left += 1
552+
while (left < right && nums_tmp(right) == nums_tmp(right - 1)) right -= 1
553+
left += 1
554+
right -= 1
555+
} else if (sum < target) left += 1
556+
else right -= 1
557+
}
558+
}
559+
}
560+
}
561+
}
562+
}
563+
}
564+
// 最终返回的res要转换为List,return关键字可以省略
565+
res.toList
566+
}
567+
}
568+
```
526569
-----------------------
527570
<div align="center"><img src=https://code-thinking.cdn.bcebos.com/pics/01二维码一.jpg width=500> </img></div>

‎problems/0019.删除链表的倒数第N个节点.md

Lines changed: 48 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@
99

1010
## 19.删除链表的倒数第N个节点
1111

12-
[力扣题目链接](https://leetcode-cn.com/problems/remove-nth-node-from-end-of-list/)
12+
[力扣题目链接](https://leetcode.cn/problems/remove-nth-node-from-end-of-list/)
1313

1414
给你一个链表,删除链表的倒数第 n 个结点,并且返回链表的头结点。
1515

@@ -39,7 +39,7 @@
3939

4040
分为如下几步:
4141

42-
* 首先这里我推荐大家使用虚拟头结点,这样方面处理删除实际头结点的逻辑,如果虚拟头结点不清楚,可以看这篇: [链表:听说用虚拟头节点会方便很多?](https://programmercarl.com/0203.移除链表元素.html)
42+
* 首先这里我推荐大家使用虚拟头结点,这样方便处理删除实际头结点的逻辑,如果虚拟头结点不清楚,可以看这篇: [链表:听说用虚拟头节点会方便很多?](https://programmercarl.com/0203.移除链表元素.html)
4343

4444
* 定义fast指针和slow指针,初始值为虚拟头结点,如图:
4545

@@ -290,5 +290,51 @@ func removeNthFromEnd(_ head: ListNode?, _ n: Int) -> ListNode? {
290290
}
291291
```
292292

293+
294+
PHP:
295+
```php
296+
function removeNthFromEnd($head, $n) {
297+
// 设置虚拟头节点
298+
$dummyHead = new ListNode();
299+
$dummyHead->next = $head;
300+
301+
$slow = $fast = $dummyHead;
302+
while($n-- && $fast != null){
303+
$fast = $fast->next;
304+
}
305+
// fast 再走一步,让 slow 指向删除节点的上一个节点
306+
$fast = $fast->next;
307+
while ($fast != NULL) {
308+
$fast = $fast->next;
309+
$slow = $slow->next;
310+
}
311+
$slow->next = $slow->next->next;
312+
return $dummyHead->next;
313+
}
314+
```
315+
316+
Scala:
317+
```scala
318+
object Solution {
319+
def removeNthFromEnd(head: ListNode, n: Int): ListNode = {
320+
val dummy = new ListNode(-1, head) // 定义虚拟头节点
321+
var fast = head // 快指针从头开始走
322+
var slow = dummy // 慢指针从虚拟头开始头
323+
// 因为参数 n 是不可变量,所以不能使用 while(n>0){n-=1}的方式
324+
for (i <- 0 until n) {
325+
fast = fast.next
326+
}
327+
// 快指针和满指针一起走,直到fast走到null
328+
while (fast != null) {
329+
slow = slow.next
330+
fast = fast.next
331+
}
332+
// 删除slow的下一个节点
333+
slow.next = slow.next.next
334+
// 返回虚拟头节点的下一个
335+
dummy.next
336+
}
337+
}
338+
```
293339
-----------------------
294340
<div align="center"><img src=https://code-thinking.cdn.bcebos.com/pics/01二维码一.jpg width=500> </img></div>

‎problems/0020.有效的括号.md

Lines changed: 23 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@
1010
1111
# 20. 有效的括号
1212

13-
[力扣题目链接](https://leetcode-cn.com/problems/valid-parentheses/)
13+
[力扣题目链接](https://leetcode.cn/problems/valid-parentheses/)
1414

1515
给定一个只包括 '(',')','{','}','[',']' 的字符串,判断字符串是否有效。
1616

@@ -400,6 +400,27 @@ bool isValid(char * s){
400400
return !stackTop;
401401
}
402402
```
403-
403+
Scala:
404+
```scala
405+
object Solution {
406+
import scala.collection.mutable
407+
def isValid(s: String): Boolean = {
408+
if(s.length % 2 != 0) return false // 如果字符串长度是奇数直接返回false
409+
val stack = mutable.Stack[Char]()
410+
// 循环遍历字符串
411+
for (i <- s.indices) {
412+
val c = s(i)
413+
if (c == '(' || c == '[' || c == '{') stack.push(c)
414+
else if(stack.isEmpty) return false // 如果没有(、[、{则直接返回false
415+
// 以下三种情况,不满足则直接返回false
416+
else if(c==')' && stack.pop() != '(') return false
417+
else if(c==']' && stack.pop() != '[') return false
418+
else if(c=='}' && stack.pop() != '{') return false
419+
}
420+
// 如果为空则正确匹配,否则还有余孽就不匹配
421+
stack.isEmpty
422+
}
423+
}
424+
```
404425
-----------------------
405426
<div align="center"><img src=https://code-thinking.cdn.bcebos.com/pics/01二维码一.jpg width=500> </img></div>

0 commit comments

Comments
(0)

AltStyle によって変換されたページ (->オリジナル) /