点击查看答案
你一定是先测算出她家比你家到学校远多少公里,然后**等她走完这些公里后,再出发**。这样就一定能相遇。相遇的节点就是答案。
1. 先把A, B两个链表的节点数计算出来。链表A的节点数为`node_count_a`,链表B的节点数为`node_count_b`。
2. 假如`node_count_b > node_count_a`,那么对链表B做`node_count_b - node_count_a`次`node = node.next` 操作。
3. 这时,两个链表同时重复进行`node = node.next`操作,直到找到相同的节点或者其中一个链表已经到尾部。
## 步骤
1. 先把A, B两个链表的节点数计算出来。链表A的节点数为`node_count_a`,链表B的节点数为`node_count_b`。
```python
node_count_a = 0
node_count_b = 0
node = headA
while node:
node_count_a += 1
node = node.next
```
2. 假如`node_count_b > node_count_a`,那么对链表B做`node_count_b - node_count_a`次`node = node.next` 操作。
```python
bigger = headA
smaller = headB
if node_count_b > node_count_a:
bigger = headB
smaller = headA
for _ in range(abs(node_count_b - node_count_a)):
bigger = bigger.next
```
3. 这时,两个链表同时重复进行`node = node.next`操作,直到找到相同的节点或者其中一个链表已经到尾部。
```python
while bigger and smaller:
if bigger == smaller:
return bigger
bigger = bigger.next
smaller = smaller.next
return None
```
## 复杂度
- 时间复杂度: `O(m + n)`.
- 空间复杂度: `O(1)`.
## Java
```java
/**
* public class ListNode {
* int val;
* ListNode next;
* ListNode(int x) {
* val = x;
* next = null;
* }
* }
*/
public class Solution {
public ListNode getIntersectionNode(ListNode headA, ListNode headB) {
var nodeCountA = 0;
var nodeCountB = 0;
var node = headA;
while (node != null) {
nodeCountA += 1;
node = node.next;
}
node = headB;
while (node != null) {
nodeCountB += 1;
node = node.next;
}
var bigger = headA;
var smaller = headB;
if (nodeCountB > nodeCountA) {
bigger = headB;
smaller = headA;
}
for (var i = 0; i < Math.abs(nodeCountB - nodeCountA); i++) {
bigger = bigger.next;
}
while (bigger != null && smaller != null) {
if (bigger == smaller) {
return bigger;
}
bigger = bigger.next;
smaller = smaller.next;
}
return null;
}
}
```
## Python
```python
# class ListNode:
# def __init__(self, x):
# self.val = x
# self.next = None
class Solution:
def getIntersectionNode(self, headA: ListNode, headB: ListNode) -> Optional[ListNode]:
node_count_a = 0
node_count_b = 0
node = headA
while node:
node_count_a += 1
node = node.next
node = headB
while node:
node_count_b += 1
node = node.next
bigger = headA
smaller = headB
if node_count_b > node_count_a:
bigger = headB
smaller = headA
for _ in range(abs(node_count_b - node_count_a)):
bigger = bigger.next
while bigger and smaller:
if bigger == smaller:
return bigger
bigger = bigger.next
smaller = smaller.next
return None
```
## JavaScript
```javascript
/**
* Definition for singly-linked list.
* function ListNode(val) {
* this.val = val;
* this.next = null;
* }
*/
var getIntersectionNode = function (headA, headB) {
let nodeCountA = 0
let nodeCountB = 0
let node = headA;
while (node != null) {
nodeCountA += 1
node = node.next
}
node = headB
while (node != null) {
nodeCountB += 1
node = node.next
}
let bigger = headA
let smaller = headB
if (nodeCountB > nodeCountA) {
bigger = headB
smaller = headA
}
for (var i = 0; i < Math.abs(nodeCountB - nodeCountA); i++) {
bigger = bigger.next
}
while (bigger != null && smaller != null) {
if (bigger == smaller) {
return bigger
}
bigger = bigger.next
smaller = smaller.next
}
return null
};
```
## C#
```csharp
/**
* public class ListNode {
* public int val;
* public ListNode next;
* public ListNode(int x) { val = x; }
* }
*/
public class Solution
{
public ListNode GetIntersectionNode(ListNode headA, ListNode headB)
{
int nodeCountA = 0;
int nodeCountB = 0;
var node = headA;
while (node != null)
{
nodeCountA += 1;
node = node.next;
}
node = headB;
while (node != null)
{
nodeCountB += 1;
node = node.next;
}
var bigger = headA;
var smaller = headB;
if (nodeCountB > nodeCountA)
{
bigger = headB;
smaller = headA;
}
for (int i = 0; i < Math.Abs(nodeCountB - nodeCountA); i++)
{
bigger = bigger.next;
}
while (bigger != null && smaller != null)
{
if (bigger == smaller)
{
return bigger;
}
bigger = bigger.next;
smaller = smaller.next;
}
return null;
}
}
```
## Ruby
```ruby
# Definition for singly-linked list.
# class ListNode
# attr_accessor :val, :next
# def initialize(val)
# @val = val
# @next = nil
# end
# end
# @param {ListNode} head_a
# @param {ListNode} head_b
# @return {ListNode}
def getIntersectionNode(head_a, head_b)
node_count_a = 0
node_count_b = 0
node = head_a
while node
node_count_a += 1
node = node.next
end
node = head_b
while node
node_count_b += 1
node = node.next
end
bigger = head_a
smaller = head_b
if node_count_b > node_count_a
bigger = head_b
smaller = head_a
end
(node_count_b - node_count_a).abs.times do
bigger = bigger.next
end
while bigger && smaller
return bigger if bigger == smaller
bigger = bigger.next
smaller = smaller.next
end
nil
end
```
## C++
```cpp
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* ListNode *next;
* ListNode(int x) : val(x), next(NULL) {}
* };
*/
class Solution {
public:
ListNode *getIntersectionNode(ListNode *head_a, ListNode *head_b) {
int node_count_a = 0;
int node_count_b = 0;
ListNode *node = head_a;
while (node) {
node_count_a += 1;
node = node->next;
}
node = head_b;
while (node) {
node_count_b += 1;
node = node->next;
}
ListNode *bigger = head_a;
ListNode *smaller = head_b;
if (node_count_b > node_count_a) {
bigger = head_b;
smaller = head_a;
}
for (int i = 0; i < abs(node_count_b - node_count_a); i++) {
bigger = bigger->next;
}
while (bigger && smaller) {
if (bigger == smaller) {
return bigger;
}
bigger = bigger->next;
smaller = smaller->next;
}
return nullptr;
}
};
```
## Go
```go
/**
* Definition for singly-linked list.
* type ListNode struct {
* Val int
* Next *ListNode
* }
*/
func getIntersectionNode(headA, headB *ListNode) *ListNode {
nodeCountA := 0
nodeCountB := 0
node := headA
for node != nil {
nodeCountA++
node = node.Next
}
node = headB
for node != nil {
nodeCountB++
node = node.Next
}
bigger := headA
smaller := headB
if nodeCountB > nodeCountA {
bigger = headB
smaller = headA
}
difference := nodeCountB - nodeCountA
if difference < 0 {
difference = -difference
}
for i := 0; i < difference; i++ {
bigger = bigger.Next
}
for bigger != nil && smaller != nil {
if bigger == smaller {
return bigger
}
bigger = bigger.Next
smaller = smaller.Next
}
return nil
}
```
## Other languages
```java
// Welcome to create a PR to complete the code of this language, thanks!
```
亲爱的力扣人,为了您更好的刷题体验,请访问 [leetcoder.net](https://leetcoder.net)。
本站敢称力扣题解最佳实践,终将省你大量刷题时间!
原文链接:[160. 相交链表 - 力扣题解最佳实践](https://leetcoder.net/zh/leetcode/160-intersection-of-two-linked-lists).
GitHub 仓库: [fuck-leetcode](https://github.com/fuck-leetcode/fuck-leetcode).