如何使用 PowerShell 从 REPL 控制台将特定 CSV 列转换为 TitleCase?

Nic*_*ers 1 linux csv powershell loops pipe

根据提供的答案修改工作:

PS /home/nicholas/powershell> 
PS /home/nicholas/powershell> Get-Content ./case.csv  | ForEach-Object ToUpper                            
FJKDLA,W
FKDSLAJF,FDJK;A
NLK;NBF;SDJF,DGDF
VNL;KKDF,BGNGFN
NVCL;V,RGS
NVKL;,THRN
VLKDF,TMMJYMF
FJDK,FDJK;A
PS /home/nicholas/powershell> 
PS /home/nicholas/powershell> Get-Content ./case.csv  | ForEach-Object ToLower 
fjkdla,w
fkdslajf,fdjk;a
nlk;nbf;sdjf,dgdf
vnl;kkdf,bgngfn
nvcl;v,rgs
nvkl;,thrn
vlkdf,tmmjymf
fjdk,fdjk;a
PS /home/nicholas/powershell> 
PS /home/nicholas/powershell> $TextInfo = (New-Object System.Globalization.CultureInfo("en-US")).TextInfo;
PS /home/nicholas/powershell> 
PS /home/nicholas/powershell> Get-Content ./case.csv  | ForEach-Object ToTitleCase                         
PS /home/nicholas/powershell> 
PS /home/nicholas/powershell> pwsh --version
PowerShell 7.3.4
PS /home/nicholas/powershell> 
PS /home/nicholas/powershell> lsb_release -a
No LSB modules are available.
Distributor ID: Ubuntu
Description:    Ubuntu 23.04
Release:    23.04
Codename:   lunar
PS /home/nicholas/powershell> 
Run Code Online (Sandbox Code Playgroud)

我主要关心的是更多地转换为 TitleCase,并且理想情况下,从 REPL 控制台而不是脚本文件进行转换。我无法更新针对特定列的工作。

我所说的 REPL 控制台是指交互式 shell,如果这有意义的话。

所有的答案和评论都非常有帮助和赞赏。

附加信息:

PS /home/nicholas/powershell> 
PS /home/nicholas/powershell> Get-Culture                                        

LCID             Name             DisplayName
----             ----             -----------
1033             en-US            English (United States)

PS /home/nicholas/powershell> 
PS /home/nicholas/powershell> (Get-Culture).TextInfo.ToTitleCase($_.fjkdla) 

PS /home/nicholas/powershell> 
PS /home/nicholas/powershell> (Get-Culture).TextInfo.ToTitleCase("hmm")     
Hmm
PS /home/nicholas/powershell> 
Run Code Online (Sandbox Code Playgroud)

这看起来是单个字符串所需的输出。但是,不确定如何从控制台迭代上面的 CSV 文件。

mkl*_*nt0 5

针对现已发生重大变化的问题进行更新:

  • 正如标题中所反映的,您最初的问题是关于CSV数据并针对特定列。鉴于您最初使用的是Import-Csv,因此需要使用OO方法,如下一节所示。

    • 要定位特定列,您需要知道其确切名称(除非大小写无关紧要)。
    • 如果您的 CSV 文件缺少 headers ,即带有列名的初始行,您需要:
      • Import-Csv通过的参数手动提供列名称-Header,例如:Import-Csv ./case.csv -Header Name, Value
      • 然后在脚本块中引用这些列名称ForEach-Object,如下所示(例如,$_.Name
  • 您更新的问题使用CSV 文件的纯文本Get-Content处理,似乎试图将所有列值转换为标题大小写;为此,请使用以下方法:

     $textInfo = (Get-Culture).TextInfo
     Get-Content ./case.csv | ForEach-Object { $textInfo.ToTitleCase($_) }
    
     # Alternatively, if performance doesn't matter and you don't want to 
     # create an aux. variable, to reduce the interactive typing effort:
     Get-Content ./case.csv | ForEach-Object { (Get-Culture).TextInfo.ToTitleCase($_) }
    
    Run Code Online (Sandbox Code Playgroud)

回答原来的 OO 问题:

要将单个已知列转换为单个管道中的标题大小写,请务必使用其确切名称(尽管大小写并不重要);使用示例 CSV 的第一列名称作为示例:

Import-Csv ./case.csv |
  ForEach-Object {
    $_.fjkdla = (Get-Culture).TextInfo.ToTitleCase($_.fjkdla)
    $_ # Output the modified object.
  }
Run Code Online (Sandbox Code Playgroud)

这里输出从CSV文件中解析出来的修改对象,直接输出;默认情况下,它们打印到屏幕上;例如,添加$csv = 到管道以捕获变量中的输出$csv

笔记:

要系统地将所有列转换为标题大小写,而无需提前知道列(属性)值,请使用内在psobject属性

Import-Csv ./case.csv |
  ForEach-Object {
    # Iterate over all properties and modify their values.
    foreach ($prop in $_.psobject.Properties) {
      $prop.Value = (Get-Culture).TextInfo.ToTitleCase($prop.Value)
    }
    $_ # Output the modified object.
  }
Run Code Online (Sandbox Code Playgroud)

笔记:

  • 为了简单起见并最大限度地减少交互式键入工作,上述解决方案Get-Culture不仅为每个对象调用获取标题大小写方法,而且在最后一种情况下,还为每个对象的每个属性调用获取标题大小写方法,这是低效的。

性能更好的替代方案,它缓存对该方法的引用并使用以下命令调用它.Invoke()

$titleCaseMethod = (Get-Culture).TextInfo.ToTitleCase
Import-Csv ./case.csv |
  ForEach-Object {
    # Iterate over all properties and modify their values.
    foreach ($prop in $_.psobject.Properties) {
      $prop.Value = $titleCaseMethod.Invoke($prop.Value)
    }
    $_ # Output the modified object.
  }
Run Code Online (Sandbox Code Playgroud)