[英]Remove all elements of a list that are substrings of other elements of the list in python
[英]Remove multiple list elements (substrings)
我有一個目錄排序列表:
lst :=
./C01
./C01/BOOST
./C01/BOOST/src
./C01/BOOST/src/template
./C01/EmployeeAdmin
./Spheres
./db01/src/scottlib # added later
./db03
./db03/src
./db03/src/examples
./db03/src/exercises
./txt2bmp
./txt2bmp/data
./txt2bmp/docs
./txt2bmp/tests
./txt2bmp/txt2bmp
./txt2bmp_COPYED
./txt2bmp_COPYED/data
./txt2bmp_COPYED/docs
./txt2bmp_COPYED/tests
./txt2bmp_COPYED/txt2bmp
./txt2bmp_cpp
./txt2bmp_cpp/doc
我試圖刪除所有子文件夾-如果存在的話-但我無法以一種不錯的,pythonic的方式刪除它。 我使用循環來做到這一點,但這是一個漫長,丑陋且難以理解的解決方案……刪除后,列表應如下所示:
lst2 :=
./C01
./Spheres
./db01/src/scottlib
./db03
./txt2bmp
./txt2bmp_COPYED
./txt2bmp_cpp
下一行是我嘗試以多種方式修改的命令,但沒有成功...
[ i for i in lst if not i.startswith(lst[0])]
也許您有一個優雅的解決方案?
在您的情況下,您可以對路徑分隔符進行簡單計數,並將其用於列表推導中的過濾,僅保留計數為1的項目:
lst2 = [i for i in lst if i.count('/')==1]
考慮到@Jean-FrançoisFabre的評論,您可以將/
替換為os.sep
,以向代碼段添加一些可移植性。
我認為這可以解決問題
lst2 = [a for a in lst if '/'.join(a.split('/')[:-1]) not in lst]
for line in lst2: print line
輸出:
./C01
./Spheres
./db03
./txt2bmp
./txt2bmp_COPYED
./txt2bmp_cpp
我首先將路徑標准化(使用os.path.relpath
),然后隔離第一個組件,然后過濾到唯一路徑(使用set
):
from os.path import relpath
def strip_tail(path):
try:
return path[:path.index("/")]
except ValueError:
return path
lst2 = list(set(strip_tail(relpath(dir)) for dir in lst))
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.