在PowerShell中逐行读取文件

时间:2015-11-04 00:37:46

标签: powershell powershell-ise

我想在PowerShell中逐行读取文件。具体来说,我想循环遍历文件,将每一行存储在循环中的变量中,并在该行上进行一些处理。

我知道Bash的等价物:

while read line do
    if [[ $line =~ $regex ]]; then
          # work here
    fi
done < file.txt

关于PowerShell循环的文档不多。

4 个答案:

答案 0 :(得分:110)

  

关于PowerShell循环的文档不多。

有关PowerShell中循环的文档很多,您可能需要查看以下帮助主题:about_Forabout_ForEachabout_Doabout_While

foreach($line in Get-Content .\file.txt) {
    if($line -match $regex){
        # Work here
    }
}

针对您的问题的另一个惯用的PowerShell解决方案是将文本文件的行传递给ForEach-Object cmdlet

Get-Content .\file.txt | ForEach-Object {
    if($_ -match $regex){
        # Work here
    }
}

而不是在循环内部进行正则表达式匹配,您可以通过Where-Object管道,以过滤您感兴趣的那些:

Get-Content .\file.txt | Where-Object {$_ -match $regex} | ForEach-Object {
    # Work here
}

答案 1 :(得分:32)

<div class="container"> <?php if(isset($_POST['uploadBtn'])){ $fileName=$_FILES['myFile']['name']; $fileTmpName=$_FILES['myFile']['tmp_name']; $fileExtension=pathinfo($fileName,PATHINFO_EXTENSION); $allowedType = array('csv'); if(!in_array($fileExtension,$allowedType)){?> <div class="alert alert-danger">INVALID FILE</div> <?php }else{ $handle = fopen($fileTmpName, 'r'); $k = 0; $hardness = array (); while (($myData = fgetcsv($handle,1000,',')) !== FALSE) { $k++; if ( $k > 13 ) { $hardness[] = $myData[3]; } } $query = "INSERT INTO metlab.resultados_dureza_junta (a_od_r1, a_od_r2, a_od_r3, a_mod_r1, a_mod_r2, a_mod_r3, a_mid_r1, a_mid_r2, a_mid_r3, a_id_r1, a_id_r2, a_id_r3,b_od_r1, b_od_r2, b_od_r3, b_mod_r1, b_mod_r2, b_mod_r3, b_mid_r1, b_mid_r2, b_mid_r3, b_id_r1, b_id_r2, b_id_r3, c_od_r1, c_od_r2, c_od_r3, c_mod_r1, c_mod_r2, c_mod_r3, c_mid_r1, c_mid_r2, c_mid_r3, c_id_r1, c_id_r2, c_id_r3, d_od_r1) VALUES ($hardness[0],$hardness[1],$hardness[2],$hardness[3], $hardness[4],$hardness[5],$hardness[6],$hardness[7], $hardness[8], $hardness[9],$hardness[10],$hardness[11], $hardness[12],$hardness[13],$hardness[14],$hardness[15], $hardness[16],$hardness[17], $hardness[18], $hardness[19], $hardness[20], $hardness[21],$hardness[22],$hardness[23], $hardness[24],$hardness[25],$hardness[26],$hardness[27], $hardness[28],$hardness[29],$hardness[30],$hardness[31], $hardness[32],$hardness[33],$hardness[34],$hardness[35], IFNULL($hardness[36],DEFAULT(0)))"; //ON $hardness[36],DEFAULT I was trying to insert something so I can solve the problem but I cant. var_dump($hardness); $run = mysql_query($query); if(!$run){ die("error in uploading file".mysql_error()); }else{ ?> <div class="alert alert-success">SUCCESS</div> <?php } } } ?> <form action="" method="post" enctype="multipart/form-data"> <h3 class="text-center"> RESULTS </h3></hr> <div class="row"> <div class="col-md-6"> <div class="form-group"> <input type="file" name="myFile" class="form-control"> </div> </div> </div> <div class="row"> <div class="col-md-6"> <div class="form-group"> <input type="submit" name ="uploadBtn" class="btn btn-info"> </div> </div> </div> </form> 表现不佳;它试图一次将文件读入内存。

C#(.NET)文件阅读器逐个读取每一行

最佳效果

Get-Content

或者

foreach($line in [System.IO.File]::ReadLines("C:\path\to\file.txt"))
{
       $line
}

[System.IO.File]::ReadLines("C:\path\to\file.txt") | ForEach-Object { $_ } 语句可能会比foreach稍快一些(有关详情,请参阅下面的评论)。

答案 2 :(得分:3)

我能够在大约 50 秒内读取一个 4GB 的日志文件,如下所示。您可以通过使用 PowerShell 将其作为 C# 程序集动态加载来使其更快。

[System.IO.StreamReader]$sr = [System.IO.File]::Open($file, [System.IO.FileMode]::Open)
while (-not $sr.EndOfStream){
    $line = $sr.ReadLine()
}
$sr.Close() 

答案 3 :(得分:0)

万能的开关在这里效果很好:

'one
two
three' > file

$regex = '^t'

switch -regex -file file { 
  $regex { "line is $_" } 
}

输出:

line is two
line is three