os/path 형식에 관계없이 경로에서 파일 이름 추출
운영 체제나 경로 형식이 무엇이든 경로에서 파일 이름을 추출하기 위해 사용할 수 있는 Python 라이브러리는 무엇입니까?
를 들어, 이 해 주었으면 c
:
a/b/c/
a/b/c
\a\b\c
\a\b\c\
a\b\c
a/b/../../a/b/c/
a/b/../../a/b/c
원하는 것을 정확하게 반환하는 기능이 있습니다.
import os
print(os.path.basename(your_path))
의 경우: 의 경우os.path.basename()
경로 "POSIX" "Windows")에서 사용됩니다."C:\\my\\file.txt"
전체 경로가 반환됩니다.
Linux 호스트에서 실행되는 대화형 python 쉘의 예는 다음과 같습니다.
Python 3.8.2 (default, Mar 13 2020, 10:14:16)
[GCC 9.3.0] on Linux
Type "help", "copyright", "credits" or "license" for more information.
>>> import os
>>> filepath = "C:\\my\\path\\to\\file.txt" # A Windows style file path.
>>> os.path.basename(filepath)
'C:\\my\\path\\to\\file.txt'
「」를 사용합니다.os.path.split
★★★★★★★★★★★★★★★★★」os.path.basename
Linux에서 스크립트를 실행하고 있으며 기존의 Windows 스타일 경로를 처리하려고 하면 실패합니다.
윈도우즈 경로는 경로 구분 기호로 백슬래시 또는 정방향 슬래시를 사용할 수 있습니다. 때문에 '이러한'은ntpath
module(Windows 상에서 실행 중인 경우 os.path와 동일)은 모든 플랫폼의 모든 경로에 대해 작동합니다(1).
import ntpath
ntpath.basename("a/b/c")
물론 파일이 슬래시로 끝나는 경우 기본 이름은 비어 있기 때문에 처리할 함수를 만듭니다.
def path_leaf(path):
head, tail = ntpath.split(path)
return tail or ntpath.basename(head)
검증:
>>> paths = ['a/b/c/', 'a/b/c', '\\a\\b\\c', '\\a\\b\\c\\', 'a\\b\\c',
... 'a/b/../../a/b/c/', 'a/b/../../a/b/c']
>>> [path_leaf(path) for path in paths]
['c', 'c', 'c', 'c', 'c', 'c', 'c']
(1) 한 가지 주의사항이 있습니다.Linux 파일명에 백슬래시가 포함되어 있을 수 있습니다.Linux에서는r'a/b\c'
입니다.b\c
a
의 「」, 「」, 「」를 참조하고 있습니다.c
b
「 」의a
폴더입니다.따라서 경로에서 슬래시와 역슬래시를 모두 사용하는 경우 올바르게 해석하려면 연관된 플랫폼을 알아야 합니다.Linux 파일 이름에는 백슬래시가 거의 사용되지 않기 때문에 일반적으로는 윈도 경로라고 가정하는 것이 안전하지만 실수로 보안 구멍이 생기지 않도록 코드를 작성할 때는 이 점에 유의하십시오.
os.path.http가 찾고 있는 함수입니다.
head, tail = os.path.split("/tmp/d/a.dat")
>>> print(tail)
a.dat
>>> print(head)
/tmp/d
python 3.4 이후에서는 다음과 같습니다.
>>> from pathlib import Path
>>> Path("/tmp/d/a.dat").name
'a.dat'
.name
합니다.
import os
head, tail = os.path.split('path/to/file.exe')
tail은 원하는 파일 이름입니다.
자세한 내용은 python os 모듈 문서를 참조하십시오.
import os
file_location = '/srv/volume1/data/eds/eds_report.csv'
file_name = os.path.basename(file_location ) #eds_report.csv
location = os.path.dirname(file_location ) #/srv/volume1/data/eds
개인적으로 좋아하는 건
filename = fullname.split(os.sep)[-1]
파일 이름을 자동으로 가져오려면 다음을 수행합니다.
import glob
for f in glob.glob('/your/path/*'):
print(os.path.split(f)[-1])
fname = str("C:\Windows\paint.exe").split('\\')[-1:][0]
이것은 : 페인트를 반환한다.실행
경로 또는 OS에 대한 분할 함수의 sep 값을 변경합니다.
하여 반환해야 .c
:
>>> import os
>>> path = 'a/b/c/'
>>> path = path.rstrip(os.sep) # strip the slash from the right side
>>> os.path.basename(path)
'c'
두 번째 레벨:
>>> os.path.filename(os.path.dirname(path))
'b'
: 제 엔 : 각엔 update update update update updatelazyr
정답을 제시했습니다.내 코드는 유닉스 시스템의 윈도 유사 경로에서는 작동하지 않으며, 반대로 유닉스 유사 경로에서는 작동하지 않습니다.
이는 Linux 및 Windows 및 표준 라이브러리에서 작동합니다.
paths = ['a/b/c/', 'a/b/c', '\\a\\b\\c', '\\a\\b\\c\\', 'a\\b\\c',
'a/b/../../a/b/c/', 'a/b/../../a/b/c']
def path_leaf(path):
return path.strip('/').strip('\\').split('/')[-1].split('\\')[-1]
[path_leaf(path) for path in paths]
결과:
['c', 'c', 'c', 'c', 'c', 'c', 'c']
파일 경로가 "/"로 끝나지 않고 디렉토리가 "/"로 구분된 경우 다음 코드를 사용하십시오.아시다시피 일반적으로 경로는 "/"로 끝나지 않습니다.
import os
path_str = "/var/www/index.html"
print(os.path.basename(path_str))
그러나 URL이 "/"로 끝나는 경우 다음 코드를 사용합니다.
import os
path_str = "/home/some_str/last_str/"
split_path = path_str.rsplit("/",1)
print(os.path.basename(split_path[0]))
그러나 일반적으로 Windows 경로에서 볼 수 있는 "\"로 표시된 경로는 다음과 같은 코드를 사용할 수 있습니다.
import os
path_str = "c:\\var\www\index.html"
print(os.path.basename(path_str))
import os
path_str = "c:\\home\some_str\last_str\\"
split_path = path_str.rsplit("\\",1)
print(os.path.basename(split_path[0]))
OS 타입을 체크하고 결과를 반환함으로써 두 기능을 하나의 함수로 결합할 수 있습니다.
일이잖아!
os.path.basename(name)
그러나 윈도우즈 파일 경로가 있는 Linux에서는 파일 이름을 가져올 수 없습니다.Windows도 마찬가지입니다.os.path는 다른 오퍼레이터 시스템에 다른 모듈을 로드합니다.
- Linux - posixpath
- Windows - npath
따라서 os.path는 항상 올바른 결과를 얻을 수 있습니다.
여기 regex 전용 솔루션이 있습니다.이 솔루션은 모든 OS의 모든 OS 경로에서 사용할 수 있을 것 같습니다.
다른 모듈은 필요하지 않으며 전처리도 필요하지 않습니다.
import re
def extract_basename(path):
"""Extracts basename of a given path. Should Work with any OS Path on any OS"""
basename = re.search(r'[^\\/]+(?=[\\/]?$)', path)
if basename:
return basename.group(0)
paths = ['a/b/c/', 'a/b/c', '\\a\\b\\c', '\\a\\b\\c\\', 'a\\b\\c',
'a/b/../../a/b/c/', 'a/b/../../a/b/c']
print([extract_basename(path) for path in paths])
# ['c', 'c', 'c', 'c', 'c', 'c', 'c']
extra_paths = ['C:\\', 'alone', '/a/space in filename', 'C:\\multi\nline']
print([extract_basename(path) for path in extra_paths])
# ['C:', 'alone', 'space in filename', 'multi\nline']
업데이트:
파일명(존재하는 경우)만 필요한 경우(즉,/a/b/
, 디르, 디르, 디르라고 .c:\windows\
를 : ), regex 를음음음음음음음음음음음음 ), ), ), ), ), ), ), ), ), ),로 변경합니다.r'[^\\/]+(?![\\/])$'
. "regex allenged"의 경우 슬래시의 양의 순방향 순방향 순방향 순방향 순방향 순방향 순방향 순방향 순방향 순방향 순방향 순방향으로 변경되어 해당 슬래시로 끝나는 경로명은 경로명의 마지막 서브디렉토리 대신 아무것도 반환하지 않습니다.물론 잠재적인 파일명이 실제로 파일명을 의미한다는 보장은 없습니다.os.path.is_dir()
★★★★★★★★★★★★★★★★★」os.path.is_file()
고용이 필요할 겁니다.
이것은 다음과 같이 일치합니다.
/a/b/c/ # nothing, pathname ends with the dir 'c'
c:\windows\ # nothing, pathname ends with the dir 'windows'
c:hello.txt # matches potential filename 'hello.txt'
~it_s_me/.bashrc # matches potential filename '.bashrc'
c:\windows\system32 # matches potential filename 'system32', except
# that is obviously a dir. os.path.is_dir()
# should be used to tell us for sure
정규식은 여기서 테스트할 수 있습니다.
확장자가 있는 파일 이름
filepath = './dir/subdir/filename.ext'
basename = os.path.basename(filepath)
print(basename)
# filename.ext
print(type(basename))
# <class 'str'>
확장자가 없는 파일 이름
basename_without_ext = os.path.splitext(os.path.basename(filepath))[0]
print(basename_without_ext)
# filename
중요한 새로운 기능 없이 하나의 솔루션으로 모든 것을 할 수 있습니다(임시 파일 작성용 임시 파일에 대해서:D).
import tempfile
abc = tempfile.NamedTemporaryFile(dir='/tmp/')
abc.name
abc.name.replace("/", " ").split()[-1]
「 」의 값을 abc.name
.'/tmp/tmpks5oksk7'
'접속합니다'를 수 ./
.replace("/", " ")
에 전화해요.split()
그러면 목록이 반환되고 목록의 마지막 요소가 다음과 같이 표시됩니다.[-1]
모듈을 Import할 필요가 없습니다.
디렉토리에 다수의 파일이 있어, 그 파일명을 리스트에 보존하는 경우.다음 코드를 사용합니다.
import os as os
import glob as glob
path = 'mypath'
file_list= []
for file in glob.glob(path):
data_file_list = os.path.basename(file)
file_list.append(data_file_list)
이중으로 뒤바뀐 길은 본 적이 없는데, 있나요? 모듈 python의 내장 os
이 경우 실패합니다. 모든 것들은 효과가 있고, 도 있다.또한 고객님께서 주신 경고입니다.os.path.normpath()
:
paths = ['a/b/c/', 'a/b/c', '\\a\\b\\c', '\\a\\b\\c\\', 'a\\b\\c',
... 'a/b/../../a/b/c/', 'a/b/../../a/b/c', 'a/./b/c', 'a\b/c']
for path in paths:
os.path.basename(os.path.normpath(path))
Windows 구분자는 Unix 파일 이름 또는 Windows 경로로 지정할 수 있습니다.Unix 구분자는 Unix 경로에만 존재할 수 있습니다.Unix 구분자가 있으면 Windows 이외의 경로를 나타냅니다.
다음으로 OS 고유의 세퍼레이터로 분리(후행 구분자 절단)한 후 가장 오른쪽의 값을 분할하여 반환합니다.못생겼지만 위의 가정에 따르면 간단하다.만약 가정이 틀렸다면, 업데이트해 주세요.이 답변은 더 정확한 조건에 맞게 업데이트 하겠습니다.
a.rstrip("\\\\" if a.count("/") == 0 else '/').split("\\\\" if a.count("/") == 0 else '/')[-1]
샘플 코드:
b = ['a/b/c/','a/b/c','\\a\\b\\c','\\a\\b\\c\\','a\\b\\c','a/b/../../a/b/c/','a/b/../../a/b/c']
for a in b:
print (a, a.rstrip("\\" if a.count("/") == 0 else '/').split("\\" if a.count("/") == 0 else '/')[-1])
완벽을 기하기 위해, 여기 있습니다.pathlib
3.2 솔루션: python 3.2+용 :
>>> from pathlib import PureWindowsPath
>>> paths = ['a/b/c/', 'a/b/c', '\\a\\b\\c', '\\a\\b\\c\\', 'a\\b\\c',
... 'a/b/../../a/b/c/', 'a/b/../../a/b/c']
>>> [PureWindowsPath(path).name for path in paths]
['c', 'c', 'c', 'c', 'c', 'c', 'c']
이 기능은 Windows와 Linux 모두에서 작동합니다.
Python 2와 Python 3에서는 pathlib2 모듈을 사용합니다.
import posixpath # to generate unix paths
from pathlib2 import PurePath, PureWindowsPath, PurePosixPath
def path2unix(path, nojoin=True, fromwinpath=False):
"""From a path given in any format, converts to posix path format
fromwinpath=True forces the input path to be recognized as a Windows path (useful on Unix machines to unit test Windows paths)"""
if not path:
return path
if fromwinpath:
pathparts = list(PureWindowsPath(path).parts)
else:
pathparts = list(PurePath(path).parts)
if nojoin:
return pathparts
else:
return posixpath.join(*pathparts)
사용방법:
In [9]: path2unix('lala/lolo/haha.dat')
Out[9]: ['lala', 'lolo', 'haha.dat']
In [10]: path2unix(r'C:\lala/lolo/haha.dat')
Out[10]: ['C:\\', 'lala', 'lolo', 'haha.dat']
In [11]: path2unix(r'C:\lala/lolo/haha.dat') # works even with malformatted cases mixing both Windows and Linux path separators
Out[11]: ['C:\\', 'lala', 'lolo', 'haha.dat']
테스트 케이스의 경우:
In [12]: testcase = paths = ['a/b/c/', 'a/b/c', '\\a\\b\\c', '\\a\\b\\c\\', 'a\\b\\c',
...: ... 'a/b/../../a/b/c/', 'a/b/../../a/b/c']
In [14]: for t in testcase:
...: print(path2unix(t)[-1])
...:
...:
c
c
c
c
c
c
c
은 모든 으로 변환하는 입니다.pathlib2
플랫폼에 따라 디코더가 다릅니다.pathlib2
에는 includes includes called called called called called called called called called called called called called라고 불리는 되어 있습니다.PurePath
모든 경로에서 작동해야 합니다.하지 않는 할 수 .fromwinpath=True
여러 입력 문자열이 분할됩니다.마지막은 찾고 있는 리프입니다.★★★★★★★★★★★★★★★★★★,path2unix(t)[-1]
.
가 ''인 nojoin=False
패스는 다시 결합되므로 출력은 단순히 UNIX 형식으로 변환된 입력 문자열이 됩니다.이 문자열은 플랫폼 간의 서브패스 비교에 도움이 됩니다.
WSL(Windows and Ubuntu)에서는 이 방법을 사용하고 있으며, (I) 예상대로 "import os"만을 사용하여 동작합니다.따라서 기본적으로 replace()는 현재 OS 플랫폼을 기반으로 올바른 경로 분리기를 배치합니다.
경로가 슬래시 '/'로 끝나는 경우 파일이 아니라 디렉터리이므로 빈 문자열을 반환합니다.
import os
my_fullpath = r"D:\MY_FOLDER\TEST\20201108\20201108_073751.DNG"
os.path.basename(my_fullpath.replace('\\',os.sep))
my_fullpath = r"/MY_FOLDER/TEST/20201108/20201108_073751.DNG"
os.path.basename(my_fullpath.replace('\\',os.sep))
my_fullpath = r"/MY_FOLDER/TEST/20201108/"
os.path.basename(my_fullpath.replace('\\',os.sep))
my_fullpath = r"/MY_FOLDER/TEST/20201108"
os.path.basename(my_fullpath.replace('\\',os.sep))
Windows(왼쪽) 및 Ubuntu(WSL 경유, 오른쪽):
언급URL : https://stackoverflow.com/questions/8384737/extract-file-name-from-path-no-matter-what-the-os-path-format
'programing' 카테고리의 다른 글
Python 스크립트에서 현재 git 해시를 가져옵니다. (0) | 2022.10.18 |
---|---|
MySQL의 트리 구조 테이블을 한 번에 조회할 수 있습니까? (0) | 2022.10.18 |
MySQL 데이터베이스의 모든 테이블에 대한 레코드 수 가져오기 (0) | 2022.10.18 |
jQuery 옵션을 선택했는지 여부를 확인합니다. 선택하지 않은 경우 기본값을 선택하십시오. (0) | 2022.10.18 |
php.ini 파일(xampp)을 찾는 방법 (0) | 2022.10.18 |