【问题标题】:Python: how to keep and/or modify partial file name?Python:如何保留和/或修改部分文件名?
【发布时间】:2016-04-06 06:58:38
【问题描述】:

我已经阅读了下面显示的线程:

Renaming filenames using python

Replacing Filename characters with python

但它们并不是我想要的。

我在这里尝试完成的是重命名文件,同时将它们从 Excel 转换为 csv。我的转换代码有效,但我也想去掉输出文件名中不必要的单词。

假设我的文件名是:

"Sample_file_2016-4-30.xlsx", "Hello_world_2014-5-30.xlsx", "Great_day_2015-1-14.xlsx"

我希望我的输出是(要删除的数字之前的所有字符):

“2016-4-30.csv”、“2014-5-30.csv”、“2015-1-14.csv”

这是我已经完成的(并且代码有效):

def xslx_to_csv():
    files = os.listdir(r"~\files to be converted")
    current_path = os.getcwd()
    os.chdir(r"~\files to be converted")

    for file in files:
        print file
        filename = os.path.splitext(file)[0]

        wb = xlrd.open_workbook(file)
        sh = wb.sheet_by_index(0)
        new_ext = 'csv'
        new_name = (filename, new_ext)
        csvfile = open(".".join(new_name), 'wb')
        wr = csv.writer(csvfile, quoting=csv.QUOTE_ALL)

        for rownum in xrange(sh.nrows):
            wr.writerow(sh.row_values(rownum))

        csvfile.close()

但是,这段代码只给了我如下输出:

"Sample_file_2016-4-30.csv", "Hello_world_2014-5-30.csv", "Great_day_2015-1-14.csv"

到目前为止我所做的尝试: 我尝试过使用os.rename() 和str.replace()(由Djizeus 建议),我也尝试过使用静态字符串位置,例如:new_name[14:35] 来获取部分名称。

但我需要一个更动态的方法。 yyyy-mm-dd格式的数字前的所有字符如何识别和去除?

额外问题: 我想更进一步,而不是仅仅从文件名中删除额外的部分,我想知道如何更改文件名。例如,在这种情况下,所需的输出可能是:

"Bonus_file_2016-4-30.csv", "Bonus_file_2014-5-30.csv", "Bonus_file_2015-1-14.csv"

所以基本上,我想用某个单词替换开头的单词,比如“Bonus”。

【问题讨论】:

  • new_name.replace('Sample', 'Bonus')
  • 请在发帖前做一些研究...
  • 嗨@Djizeus你的答案可能适合这个例子,但我怎样才能让它更有活力?如果我的文件不是以相同的字符串“Sample”开头怎么办?
  • 那么你应该首先查看 Python 字符串文档,查看可用的方法以及你可以用它们做什么。如果这样你不能做你喜欢的事情或让它们工作,那么你可以在这里询问并告诉我们你正在尝试做什么(文件名的格式和预期的输出),以及到目前为止你尝试了什么。另见:minimal reproducible example.
  • @Djizeus 非常感谢您的 cmets。我已经通读了它们,并添加了到目前为止我尝试过的部分。现在符合标准了吗?就像我说的,我对 Python 完全陌生,还不太擅长研究它。谢谢你对我的耐心

标签: python regex string


【解决方案1】:

当基于固定索引的切片或替换已知子字符串不足以满足您的需求时,您必须求助于regular expressions。它本身就是一个庞大且相当复杂的主题,本质上它们是您可以用来搜索字符串的小程序。

在您的特定情况下,您可以使用例如以下正则表达式:\d{4}-\d{1,2}-\d{1,2}$。意思是:

  • \d{4}:4 位,
  • -:后跟一个破折号,
  • \d{1,2}:后跟1或2位数字,
  • -:后跟一个破折号,
  • \d{1,2}:后跟 1 位或 2 位数字,
  • $: 后面是字符串的结尾。

你会这样使用它:

import re

# Compile the regular expression
# r'' is to give a raw string and avoid escaping \ characters
prog = re.compile(r'\d{4}-\d{1,2}-\d{1,2}$')

#Search the regular expression in filename
res = prog.search(filename)

#This gives you the start position of the date
#(assuming all filenames end with a date)
date_start = res.start()
new_name = 'Bonus_file_%s.csv' % filename[date_start:]

【讨论】:

  • 啊,非常感谢!!!这正是我需要的!所以一个附带问题,如果你认为这是一个非常愚蠢的问题,你不必回答我,但为什么要先使用 compile() 呢?
  • 这不是一个愚蠢的问题:) 其实你不需要,你也可以使用快捷方式res = re.search(r'\d{4}-\d{1,2}-\d{1,2}$', filename)。我这样做是出于习惯,但只有当您要多次使用相同的正则表达式时,编译才有用。通过编译它,您的程序将只解析一次表达式,从而节省时间。参考文献有关详细信息,请参阅 Python 文档。
  • 好的,我现在明白了!这就像先将其保存为变量/对象,然后您可以一遍又一遍地使用它,而无需输入所有详细信息。非常感谢!
猜你喜欢
  • 2011-05-21
  • 2023-03-10
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-11-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多