需要在shell脚本中拆分文件名form _ some number

vsnjm48y  于 2023-01-17  发布在  Shell
关注(0)|答案(3)|浏览(142)

我在目录中有一些文件,需要按_ number拆分它们
示例:我有一些文件,如ODRD_AzureData_Linux_x64_19.1.0.0.7.tar,
我想把它分成
名称:ODRD_蓝色数据_Linux_x64
版本号:19.1.0.0.7
我尝试了这个没有得到结果:名称='$文件名|cut -f1 -d“.”“,我没有得到预期的结果,
请帮帮我

pbpqsu0x

pbpqsu0x1#

您可以使用bash glob参数扩展作为explained herehere来提取文件名和版本号,并将它们存储在bash数组中(假设有多个扩展名为.tar的文件)。
我已经为您编写了一个简单的bash脚本(命名为listfiles.sh),您可以根据需要参考和修改它:

#!/bin/bash

declare -a arrFiles
declare -a fname
declare -a fversion

for file in "$1"/*
do
    arrFiles=("${arrFiles[@]}" "$file")
done

idx=0
for f in "${arrFiles[@]}"
do
    extension="${f##*.*.}"
    fname=("${fname[@]}" "$(basename -s ".$extension" "${f}")")
    fversion=("${fversion[@]}" "${fname[idx]#*_[0-9]}")
#    echo ${fversion[idx]}
    idx=$((idx+1))
done

echo "FileName: " "${fname[@]%_*}"
echo "Version: " "${fversion[@]}"

要使用它,您需要在存储文件的文件夹上调用此脚本,例如:
bash listfiles.sh Documents

oxiaedzo

oxiaedzo2#

为了与POSIX shell兼容,并避免产生多个进程(subshell),您可以使用POSIX shell支持的内置参数扩展,根据需要从文件名的左右两端进行修剪,将文件名分解为您想要的namever。基本方法是在目录中循环文件名并应用参数扩展,如下所示:

#!/bin/sh

for f in *; do                # loop over each file in current directory
  [ ! -f "$f" ] && continue   # skip anything not a file
  name="${f%_*}"              # trim from right to first '_'
  ver="${f##*_}"              # trim from left to last '_'
  ver="${ver%.*}"             # trim from right to first '.'
  printf "name: %s\nver:  %s\n" "$name" "$ver"    # output results
done

POSIX支持的参数扩展包括:

${var#pattern}      # Strip shortest match of pattern from front of $var
    ${var##pattern}     # Strip longest match of pattern from front of $var
    ${var%pattern}      # Strip shortest match of pattern from back of $var
    ${var%%pattern}     # Strip longest match of pattern from back of $var

注意:pattern可以包含正常的全局匹配字符,如'*'

示例输出

对于上面的示例,您将收到以下输出:

name: ODRD_AzureData_Linux_x64
ver:  19.1.0.0.7
cnh2zyt3

cnh2zyt33#

要给予一个包罗万象的解决方案有点困难,因为我们不确定它的格式或shell,但让我们假设:

  • Shell是BASH(或任何符合POSIX的Shell)
  • 格式始终为名称_版本。*

你可以使用参数展开来很好地解决这个问题。

#!/bin/bash

<SNIPPED>

# This doesn’t have to be hard-coded, it’s just for simplicity
input=ODRD_AzureData_Linux_x64_19.1.0.0.7.tar

# Remove the lastmost ‘_’ and everything after.
name=“${input%_*}”

# Remove the lastmost ‘_’ and everything before.
version=“${input%*_}

# Remove the firstmost ‘.’ with a letter following
# and everything after.
version=“${version#.[a-zA-Z]*}

# ^ We need to do this to remove the extension.
# This may break if version includes “alpha/beta”

<SNIPPED>

这个特殊的过程被称为“模式删除”。然而,Bash参数扩展有很多巧妙的技巧,我建议你去看看。
阅读大卫的评论后,我了解到参数扩展的一个子集是符合POSIX的,并相应地调整了我的答案。

相关问题