052 · Crawler Log Folder
My First Thoughts
嗯,这道题的输入变成了字符串 list。
里面主要有几类操作:
"../"表示回到上一层,实际深度应该-1"./"表示当前层不动,实际深度应该+0- 像
"d1/"、"d21/"这样的字符串表示进入下一层,实际深度应该+1
所以好像直接维护一个结果就行。
题目问的是:最后至少需要多少次 "../" 才能回到主文件夹。这个答案其实就是“当前离主文件夹有几层”。
那可以先定义:
result = 0result 表示当前在主文件夹下面第几层。刚开始就在主文件夹,所以是 0。
然后遍历 logs:
result = 0
for char in logs:
if char == "./":
result += 0
elif char == "../":
if result != 0:
result -= 1
else:
next
else:
result += 1
return result这个思路里有一个很关键的问题:
需要新 list 来装路径吗?
一开始会觉得这题和前几道栈题很像,所以可能要维护一个 list,把进入过的文件夹放进去,遇到 "../" 就 pop。
但这里再看一下题目要求,它并没有问当前完整路径是什么,也没有问当前在哪个具体文件夹里。它只问回到主文件夹还要几步。
如果只问还要几步,那文件夹名字其实不重要,只要知道当前深度就够了。
所以 result 这个整数方向是对的。
Why That Is Not Enough
上面的算法想法是正确的:这题可以不用 list,只维护深度。
真正需要调整的是两个实现细节。
第一个是变量名。
这里遍历的是 logs,每个元素不是单个字符,而是一次操作,比如 "../"、"./"、"d1/"。所以变量名用 log 会比 char 更准确:
for log in logs:第二个是这段:
else:
nextPython 里的 next 不是“跳过这次循环”的意思。这里其实不需要做任何事。
当 result == 0 时,说明已经在主文件夹。再遇到 "../",题目说仍然留在主文件夹,所以 result 保持 0 就行。
也就是说,可以直接不写这个 else。
另外,"./" 时写:
result += 0虽然不会错,但它什么也没有改变。可以写成 pass,也可以把 "./" 放到最后自然忽略。
Final Idea
继续使用 result,让它表示当前目录深度。
从主文件夹开始:
result = 0然后依次处理每个 log:
- 如果
log == "../",说明要回到上一层;只有result > 0时才能减一 - 如果
log == "./",说明停在当前文件夹,什么都不做 - 否则,它一定是进入某个子文件夹,比如
"d1/",深度加一
因为最终要回到主文件夹,而每次 "../" 只能往上一层,所以最后的 result 就是答案。
这题也可以用 list 模拟完整路径,但那是保存了更多信息:
["d1", "d21"]
最后再返回 list 的长度。
而这题不需要具体路径名,所以可以把 list 简化成一个整数深度:
2
Why It Works
result 始终表示当前文件夹距离主文件夹有几层。
开始时位于主文件夹,所以:
result = 0当遇到一个子文件夹操作,比如 "d1/",位置会从当前文件夹进入下一层,所以深度增加:
result += 1当遇到 "../",位置会回到上一层。如果当前深度大于 0,就可以减少一层:
result -= 1但如果 result 已经是 0,说明已经在主文件夹。题目规定不能移动到主文件夹之上,所以此时保持 0。
当遇到 "./",位置不变,深度自然也不变。
遍历结束后,result 表示当前位置距离主文件夹的层数。要回到主文件夹,每执行一次 "../" 只能减少一层,所以最少需要的次数正好就是 result。
比如:
logs = ["d1/", "d2/", "../", "d21/", "./"]
深度变化是:
0 -> 1 -> 2 -> 1 -> 2 -> 2
最后深度是 2,所以答案是 2。
Code
def minOperations(logs):
result = 0
for log in logs:
if log == "../":
if result > 0:
result -= 1
elif log != "./":
result += 1
return resultComplexity
| Time | \(O(n)\) - n 是 logs 的长度;每个操作只处理一次 |
| Space | \(O(1)\) - 只用一个整数 result 保存当前深度 |
Takeaway
遇到看起来像栈的问题时,先确认题目到底要不要完整状态。如果只需要知道“还剩几层”这种数量信息,就可以把栈里的具体内容简化成一个计数器。数据结构要服务于返回值,不一定要把所有过程都保存下来。
← Quiz