在 R 中获取不带扩展名的文件名



>我有一个文件:

ABCD.csv 

.csv之前的长度不是固定的,并且以任何长度变化。

如何提取.csv前的部分?

标准安装工具包中有一个内置file_path_sans_ext,可以抓取没有扩展名的文件。

tools::file_path_sans_ext("ABCD.csv")
## [1] "ABCD"

basename也会删除指向文件的路径。使用此正则表达式,将删除任何扩展名。

filepath <- "d:/Some Dir/ABCD.csv"
sub(pattern = "(.*)\..*$", replacement = "\1", basename(filepath))
# [1] "ABCD"

或者,按照泰勒·林克(Tyler Rinker(的建议使用file_path_sans_ext

file_path_sans_ext(basename(filepath))
# [1] "ABCD"

您可以使用subsubstr

sub('\.csv$', '', str1) 
#[1] "ABCD"

substr(str1, 1, nchar(str1)-4)
#[1] "ABCD"

使用@JasonV帖子中的"file_path">

sub('\..*$', '', basename(filepath))
#[1] "ABCD"

library(stringr)
str_extract(filepath,  perl('(?<=[/])([^/]+)(?=\.[^.]+)'))
#[1] "ABCD"

数据

str1 <- 'ABCD.csv'
fs::path_ext_remove()">

删除最后一个扩展名并返回路径的其余部分"。

fs::path_ext_remove(c("ABCD.csv", "foo.bar.baz.txt", "d:/Some Dir/ABCD.csv"))
# Produces: [1] "ABCD"             "foo.bar.baz"      "D:/Some Dir/ABCD"

你也可以试试这个:

data <- "ABCD.csv"
gsub(pattern = "\.csv$", "", data)
#[1] "ABCD"

这在文件列表的情况下也很有帮助,比如

data <- list.files(pattern="\.csv$") ,使用该代码将删除列表中所有文件的扩展名。

如果您有具有多个(可能的扩展名(的文件名,并且只想去除最后一个扩展名,则可以尝试以下操作。

考虑foo.bar.baz.txt文件名

sub('\..[^\.]*$', '', "foo.bar.baz.txt")

会给你留下foo.bar.baz.

下面是一个适用于压缩和多个文件的实现:

remove.file_ext <- function(path, basename = FALSE) {
  out <- c()
  for (p in path) {
    fext <- file_ext(path)
    compressions <- c("gzip", "gz", "bgz", "zip")
    areCompressed <- fext %in% compressions
    if (areCompressed) {
      ext <- file_ext(file_path_sans_ext(path, compression = FALSE))
      regex <- paste0("*\.",ext,"\.", fext,"$")
    } else {
      regex <- paste0("*\.",fext,"$")
    }
    new <- gsub(pattern = regex, "", path)
    out <- c(out, new)
  }
  return(ifelse(basename, basename(out), out))
}

加载所需的库:

> library(stringr)

从正则表达式中提取所有匹配项:

> str_match("ABCD.csv", "(.*)\..*$")
     [,1]       [,2]  
[1,] "ABCD.csv" "ABCD"

仅返回结果的第二部分,对应于与文件名匹配的组:

> str_match("ABCD.csv", "(.*)\..*$")[,2]
[1] "ABCD"

编辑@U-10-前进:

它与另一个答案的原理基本相同。只是我发现这个解决方案更强大。

正则表达式明智,这意味着:

  • (( = 组

  • .* = 除换行符以外的任何单个字符任意时间数

  • //是
  • 转义符号,因此//. 字面意思是".">

  • .* = 任意字符任意次数

  • $ 表示应位于输入字符串的末尾

逻辑是,它将返回 "." 前面的组,后跟字符串末尾的一组字符(在本例中等于文件扩展名(。

上面的答案很棒,但我对一次处理数百万条路径最快的答案感兴趣。 似乎通过这个 SO 问题使用 sub 是将文件名从路径中取出的最快方法。 然后比较上面的三种方法,使用tools::file_path_sans_ext更快。

library(fs)
library(stringr)
library(microbenchmark)
files<-paste0("http://some/ppath/to/som/cool/file/",1:1000,".flac")
microbenchmark(
    fs::path_ext_remove(sub(".*/", "", files)),
    tools::file_path_sans_ext(sub(".*/", "", files)),
    str_extract(files,  '(?<=[/])([^/]+)(?=\.[^.]+)')
    
) 
Unit: milliseconds
                                                expr     min       lq      mean   median      uq     max neval
          fs::path_ext_remove(sub(".*/", "", files)) 10.6273 10.98940 11.323063 11.20500 11.4992 14.5834   100
    tools::file_path_sans_ext(sub(".*/", "", files))  1.3717  1.44260  1.532092  1.48560  1.5588  2.4806   100
 str_extract(files, "(?<=[/])([^/]+)(?=\\.[^.]+)")  7.4197  7.62875  7.985206  7.88835  8.2311  9.4107   100

相关内容

最新更新