将文件名作为单独变量存储在PowerShell中-基于特定字符

将文件名作为单独变量存储在PowerShell中-基于特定字符,powershell,Powershell,我有一个以特定格式存储的供应商文件,我想使用PowerShell将文件名转换为三个单独的变量,然后使用这些变量传递给将要执行的存储过程 文件格式如下所示: AA_BBBBB_YYYYMMDD.xlsx 例如,以下是当前Excel文件的示例: TX_StampingFee_20210303.xlsx 第一个字符通常是美国各州的缩写,但并不总是如此,因此可以是2或3个字符长。第二部分是Excel文件包含的费用类型,而最后一部分是YYYYMMDD格式的日期 我要做的是让PowerShell读取文件名

我有一个以特定格式存储的供应商文件,我想使用PowerShell将文件名转换为三个单独的变量,然后使用这些变量传递给将要执行的存储过程

文件格式如下所示:

AA_BBBBB_YYYYMMDD.xlsx

例如,以下是当前Excel文件的示例:

TX_StampingFee_20210303.xlsx
第一个字符通常是美国各州的缩写,但并不总是如此,因此可以是2或3个字符长。第二部分是Excel文件包含的费用类型,而最后一部分是YYYYMMDD格式的日期

我要做的是让PowerShell读取文件名,并将文件名分为三个单独的变量:

$State
$Fee
$Date
到目前为止,我将列出目录中的Excel文件,然后我尝试拆分名称-但我相信名称上的文件扩展名会导致错误。我如何根据“u”(下划线)字符将此文件名拆分为单独的变量

Foreach ($file in Get-Childitem "C:\PowerShell\Test\*.xlsx") {
    $file.name
}

$filenames = (Get-ChildItem -Path "C:\PowerShell\Test\*.xlsx" -Directory).Name

Write-Host $filenames

$chararray = $filenames.Split("_")
$chararray

您可以将basename作为目标,它是文件名减去扩展名。然后,当你分成3个部分时,你可以直接把它们分成3个变量

Foreach ($file in Get-Childitem "C:\PowerShell\Test\*.xlsx") {
    $State,$Fee,$Date = $file.basename.split('_')
    Write-Host State: $State Fee: $Fee Date: $Date
}

您可以将basename作为目标,它是文件名减去扩展名。然后,当你分成3个部分时,你可以直接把它们分成3个变量

Foreach ($file in Get-Childitem "C:\PowerShell\Test\*.xlsx") {
    $State,$Fee,$Date = $file.basename.split('_')
    Write-Host State: $State Fee: $Fee Date: $Date
}

使用
BaseName
而不是
Name
属性获取不带扩展名的文件名

然后,如果您信任文件名的模式,则可以在数组中索引一个范围,将1+费用类型的子字符串合并为单个字符串:

$filenames = (Get-ChildItem -Path "C:\PowerShell\Test\*.xlsx" -File).BaseName

if ($filenames) {
    [System.Collections.ArrayList]$fees = @()
    [System.Collections.ArrayList]$states = @()
    [System.Collections.ArrayList]$dates = @()

    foreach ($name in $filenames) {
        $chararray = $name.Split("_")
        $arrlen = $chararray.length

        if ($arrlen -ge 3) {
            $states += $chararray[0]
            $fees += $chararray[1..$arrlen-2] -join '_'
            $dates += $chararray[$arrlen])
        }
    }
}

使用
BaseName
而不是
Name
属性获取不带扩展名的文件名

然后,如果您信任文件名的模式,则可以在数组中索引一个范围,将1+费用类型的子字符串合并为单个字符串:

$filenames = (Get-ChildItem -Path "C:\PowerShell\Test\*.xlsx" -File).BaseName

if ($filenames) {
    [System.Collections.ArrayList]$fees = @()
    [System.Collections.ArrayList]$states = @()
    [System.Collections.ArrayList]$dates = @()

    foreach ($name in $filenames) {
        $chararray = $name.Split("_")
        $arrlen = $chararray.length

        if ($arrlen -ge 3) {
            $states += $chararray[0]
            $fees += $chararray[1..$arrlen-2] -join '_'
            $dates += $chararray[$arrlen])
        }
    }
}


太棒了-非常感谢!实际上,您的示例文件有4个部分。您的中间部分也会有下划线吗?我们可以让供应商在描述费用时不包含下划线,这样我们的文件名中就只有两个下划线。好的。您可以编辑您的示例文件,以减少未来访问者可能遇到的混淆。太棒了-非常感谢!实际上,您的示例文件有4个部分。您的中间部分也会有下划线吗?我们可以让供应商在描述费用时不包含下划线,这样我们的文件名中就只有两个下划线。好的。您可以编辑示例文件,以减少未来访问者可能产生的混淆。OP询问的是文件-而不是
-目录
!;-)。。。您正在从所有
$filenames
(实际上是目录名)构建
$chararray
,而不仅仅是从当前文件名。真的,真的。应该从头开始写,而不是复制粘贴。编辑。如果我没弄错的话,这个
$fees+=$chararray[1..$arrlen-2]-join'
应该是这个
$fees+=$chararray[1..$arrlen-2]-join'
这个
$dates+=$chararray[$arrlen-2])
应该是这个
$dates+=$chararray[$array[$arrlen-1]
。。。您可以在发布代码之前先试用它。;-)不管这些:我可以想象,如果一个文件名和它的部分名称能够一起处理,那将是一件好事如果您完成了额外的步骤,请使用.NET arraylist,然后正确使用它,不要使用+=来添加元素,请使用.add()方法。它的速度更快。例如,从0到50000的简单循环使用+=将$x的值添加到数组需要53.23秒。使用.Add()方法进行完全相同的循环只需82.14毫秒OP询问的是文件-而不是
-目录
!;-)。。。您正在从所有
$filenames
(实际上是目录名)构建
$chararray
,而不仅仅是从当前文件名。真的,真的。应该从头开始写,而不是复制粘贴。编辑。如果我没弄错的话,这个
$fees+=$chararray[1..$arrlen-2]-join'
应该是这个
$fees+=$chararray[1..$arrlen-2]-join'
这个
$dates+=$chararray[$arrlen-2])
应该是这个
$dates+=$chararray[$array[$arrlen-1]
。。。您可以在发布代码之前先试用它。;-)不管这些:我可以想象,如果一个文件名和它的部分名称能够一起处理,那将是一件好事如果您完成了额外的步骤,请使用.NET arraylist,然后正确使用它,不要使用+=来添加元素,请使用.add()方法。它的速度更快。例如,从0到50000的简单循环使用+=将$x的值添加到数组需要53.23秒。使用.Add()方法执行完全相同的循环只需82.14毫秒