LeetCode 738.单调递增的数字
力扣题目链接
本题的核心是若当前数字不是递增的,找到需要减1 的位置,后面全部改为9,比如332
改为299
,12200
改为11999
。
- 从后向前遍历每个数字,如果
nums[i-1] > nums[i]
,则nums[i-1] -= 1
,并且记录当前的索引idx = i-1
- 再向前比较,如果还需要修改,更新当前的索引
idx
。目的是为了找到需要减1的位置。因为仔细想一下,只需要某一个位置-1,后面全变成9即可,这样才能保证数字尽可能大
class Solution:
def monotoneIncreasingDigits(self, n: int) -> int:
# string = str(n)
nums = [int(x) for x in str(n)]
result = nums[:]
length = len(nums)
if length == 1:
return n
# 寻找需要 减1 的位置
idx = -1
for i in range(length - 1, 0, -1):
if nums[i - 1] > nums[i]:
nums[i - 1] -= 1
idx = i - 1
if idx == -1: # 原本就是递增的
return n
else:
# 需要减1 的位置后面全部改为9
result[idx] -= 1
for i in range(idx+1, length):
result[i] = 9
result = int(''.join(map(str, result)))
return result
LeetCode 968.监控二叉树
思路:摄像头可以覆盖上中下三层,如果将摄像头放在叶子节点上就浪费了一层覆盖范围,所有优先放在叶子节点的父节点上,然后隔两个节点放一个摄像头。
首先我们为每个节点定义三种状态:
- 0: 无覆盖
- 1: 有摄像头
- 2: 有覆盖
由于我们从叶子节点开始考虑如何放摄像头,应该用后序遍历(左右中),由左右孩子的状态推导中间节点的状态
- 情况一:左右节点都有覆盖,此时该节点应无覆盖(等着该节点的父节点添加摄像头来覆盖)
- 情况二:左右节点至少有一个无覆盖的情况,此时该节点需添加摄像头,全局变量摄像头数量+=1
- 情况三:左右节点至少有一个有摄像头,此时该节点是有覆盖状态(情况二优先于情况三)
此外还需考虑空节点的状态,空节点是叶子节点的子节点,为了在叶子节点的父节点上放摄像头,叶子节点应是无覆盖状态,则空节点应是有覆盖状态,才能满足情况一使得叶子节点无覆盖。
这三种情况囊括了所有情况,递归返回的值为根结点的状态,如果此时根结点未被覆盖(情况一的特殊情况,即根结点没有父节点),需要在根结点加一个摄像头
class Solution:
def __init__(self):
self.result = 0
def minCameraCover(self, root: Optional[TreeNode]) -> int:
if self.traversal(root) == 0: # 根结点未被覆盖
self.result += 1
return self.result
def traversal(self, node):
if not node: return 2
left = self.traversal(node.left)
right = self.traversal(node.right)
# 情况一
if left == 2 and right == 2:
return 0
# 情况二
if left == 0 or right == 0:
self.result += 1
return 1
# 情况三
if left == 1 or right == 1:
return 2
今日毕!