LeetCode136 只出现一次的数字
Given a non-empty array of integers nums,
every element appears twice except for one. Find that single one.
Follow up: Could you implement a solution with a linear runtime complexity
and without using extra memory?
思路:位运算(异或)下面的解释和代码出自LeetCode 136 只出现一次的数字 Python解题记录。
位运算--异或
0 ^ X = X
X ^ X = 0
X ^ Y = 1
相同的元素异或为 0 , 0 和只出现一次的元素异或为该元素,可以计算出只出现一次的元素。
class Solution:
def singleNumber(self, nums: List[int]) -> int:
ret = 0
for num in nums:
ret ^= num
return ret
更详细的解释:LeetCode136 只出现一次的数字官方解决方案。
LeetCode141 环形链表
Given head, the head of a linked list,
determine if the linked list has a cycle in it.
There is a cycle in a linked list if there is some node in the list
that can be reached again by continuously following the next pointer.
Internally, pos is used to denote the index of the node
that tail's next pointer is connected to.
Note that pos is not passed as a parameter.
Return true if there is a cycle in the linked list. Otherwise, return false.
思路一:哈希表:
当某个结点在被访问时,发现存在于哈希表中,那么我们可以判断该链表为环形链表。
否则继续访问,直至结点为空。
代码出自141. 环形链表。
class Solution:
def hasCycle(self, head: ListNode) -> bool:
hash_map = {}
# 结点非空时
while head:
# 先判断结点是否已经存在于哈希表中
# 存在,则表示存在环
if head in hash_map:
return True
# 记录访问的节点,访问过都标记为 1
hash_map[head] = 1
head = head.next
return False
思路二:快慢指针
使用两个指针slow和fast分别遍历链表,fast指针遍历的速度是slow的两倍,如果两个指针能重叠,就说明这个链表是有环的。
注意点如何判断重叠?is是python中判断两个对象是否是同一个对象(内存地址一致),所以可以用is来判断slow和fast指向的是不是同一个节点。
代码出自Python LeetCode-141. 环形链表(难度-简单)(python)。
class Solution(object):
def hasCycle(self, head):
"""
:type head: ListNode
:rtype: bool
"""
fast = slow = head
while fast and fast.next:
slow = slow.next
fast = fast.next.next
if slow is fast:
return True
else:
return False
LeetCode142 环形链表 II
Given a linked list, return the node where the cycle begins.
If there is no cycle, return null.
There is a cycle in a linked list if there is some node in the list
that can be reached again by continuously following the next pointer.
Internally, pos is used to denote the index of the node
that tail's next pointer is connected to.
Note that pos is not passed as a parameter.
Notice that you should not modify the linked list.
思路一:哈希表
一个指针,节点存在就把节点存进set里,如果有环,那么入环节点会再一次被访问到,但是set中已经有这个节点了,所以直接返回该节点。
代码出自LeetCode 142 环形链表 II Linked List Cycle II Python。
class Solution(object):
# 1.set记录
def detectCycle(self, head):
"""
:type head: ListNode
:rtype: ListNode
"""
rec = []
curr = head
while curr:
if curr in rec:
return rec[rec.index(curr)]
rec.append(curr)
curr = curr.next
return None
思路二:快慢指针
代码和解释出自利特码142循环列表二,Leetcode142,环形,链表,II。
slow每次走一步,fast每次走两步,如果有环就一定会相遇。
第一次相遇时,slow走过的长度为s,fast走过的长度为f,则有:
1)fast每次走两步,slow每次走一步,所以f=2s
2)fast和slow第一次相遇时,fast走过的长度为f=s+nb(s=a+x,x是slow在环内走过的长度,
未知,但是fast要追上slow,必定有这样的关系式)
3)于是:f=2nb,s=nb
4)考虑一个指针,让它从链表头部开始走,那么回到入环节点时走过的长度必定为a+nb
5)那么slow指针走了nb了,再走a步不就回到入环节点了吗?
6)于是,令fast=head
fast从head开始每次走一步,slow也每次走一步,fast走过a步到达入环节点时,
slow也走过nb+a步到达入环节点,此时返回。
class Solution(object):
def detectCycle(self, head):
"""
:type head: ListNode
:rtype: ListNode
"""
slow = head
fast = head
while True:
if not fast or not fast.next:
return None
slow = slow.next
fast = fast.next.next
if slow == fast:
break
fast = head
while fast != slow:
slow = slow.next
fast = fast.next
return slow
任务链接
team-learning-program/LeetCodeTencent/136 只出现一次的数字.md
team-learning-program/LeetCodeTencent/141 环形链表.md
team-learning-program/LeetCodeTencent/142 环形链表 II.md