简体   繁体   English

Powershell Function elseif语句不起作用

[英]Powershell Function elseif statement not working

I have a powershell function that is not working the way it should. 我有一个Powershell函数无法正常工作。 It is supposed to limit the choices given to it in $prm to a maximum of 5. More than 5 it should alert the user. 应当将$ prm中给它的选择限制为最多5个。如果超过5个,它将提醒用户。 If 0 is passed in the string then default to null. 如果在字符串中传递了0,则默认为null。

Can someone advise what I need to do to fix this: 有人可以建议我需要做些什么来解决此问题:

Function GetListValues($prm, $charCount){ 

$buildStr="Call db.Fruit(" 

#no selection
if ($charCount -eq 0 ){ 
    $buildStr = $buildStr + "NULL,NULL,NULL,NULL,NULL);"
    write $buildStr
}elseif($charCount -ge 1 -and $charCount -le 4 ){

#selections made with then 5 parameter range

$arr = $prm.split(",");
if ($arr[0]) { $buildStr = $buildStr  + $arr[0] + "," } else { $buildStr = $buildStr + "Null," }
if ($arr[1]) { $buildStr  = $buildStr + $arr[1] + "," } else { $buildStr = $buildStr + "Null," }
if ($arr[2]) { $buildStr  = $buildStr + $arr[2] + "," } else { $buildStr = $buildStr + "Null," }
if ($arr[3]) { $buildStr  = $buildStr + $arr[3] + "," } else { $buildStr = $buildStr + "Null," }
if ($arr[4]) { $buildStr  = $buildStr + $arr[4] + ");" } else {$buildStr =  $buildStr + "Null);" }

write $buildStr


}else{
# too many selections

[System.Windows.MessageBox]::Show('Too many selections! A maximum of 5 only!')


}


}
$prm = "'Apple','Orange','Pear','Banana','Grapes'"
$charCount = ($prm.ToCharArray() | Where-Object {$_ -eq ','} | Measure-Object).Count
GetListValues $prm, $charCount

Your problem is with your test code, not your Function. 您的问题出在您的测试代码,而不是您的功能。 For powershell, you only use spaces to delimit parameters, not commas. 对于powershell,您仅使用空格来分隔参数,而不使用逗号。

So if you change your test to 因此,如果您将测试更改为

GetListValues $prm $charCount

Then the code works. 然后代码起作用。

You can ignore my earlier comment, as I assumed that your $charCount value was being set to the number of elements. 您可以忽略我之前的评论,因为我假设您将$ charCount值设置为元素数。 But on closer inspection I see that you are just counting the number of commas, and so the number of elements will be #commas + 1 (as long as you have >1 elements) 但是仔细检查,我发现您只是在计算逗号的数量,因此元素的数量将是#逗号+ 1(只要您有> 1个元素)

BTW, the $charCount is somewhat redundant, as the Function could work this out for itself, and would make the function more resilient as it would remove the possibility of the calling code passing inconsistent values. 顺便说一句,$ charCount有点多余,因为Function可以自己解决这个问题,并且可以使函数更具弹性,因为它将消除调用代码传递不一致值的可能性。

DeanOC's helpful answer points out your immediate problem with the argument-passing syntax. DeanOC的有用答案指出了使用参数传递语法的直接问题。

Additionally, as he suggests, you needn't determine the element count outside the function - it's easier and more robust to let the function itself handle that. 此外,正如他所建议的那样,您无需确定函数外部的元素数量-让函数本身处理该函数更容易且更可靠。 Here's a PowerShell-idiomatic reformulation of your function that does just that: 这是功能的PowerShell惯用的表述,它就是这样做的:

function GetListValues {
  param(
    [ValidateCount(0,5)] # Allow between 0 and 5 values.
    [string[]] $Columns
  )
  # Create a 5-element array filled with the input column names
  # and 'Null' for any remaining elements.
  $allColumns = New-Object string[] 5
  for ($i = 0; $i -lt $allColumns.Count; ++$i) {
    $allColumns[$i] = if ($i -lt $Columns.Count) { $Columns[$i] } else { 'Null' }
  }
  # Use string expansion (interpolation) to construct the output string.
  "Call db.Fruit($($allColumns -join ','))"
}

Defining the parameter as [string[]] allows you to (a) pass the column names individually and (b) easily gives you access to their count and allows you to constrain the acceptable range of column names via the ValidateCount attribute. 通过将参数定义为[string[]] ,您可以(a)分别传递列名,并且(b)可以轻松访问它们的计数,并可以通过ValidateCount属性来限制可接受的列名范围。

Therefore you can call the function above as follows: 因此,您可以按以下方式调用上面的函数:

# Pass 5 column names.
# Note that with the simple names at hand you needn't even quote them.
PS> GetListValues Apple, Orange, Pear, Banana, Grapes

Call db.Fruit(Apple,Orange,Pear,Banana,Grapes)

# Pass no column names at all.
PS> GetListValues

Call db.Fruit(Null,Null,Null,Null,Null)

# Pass too many names -> ValidateCount triggers an error.
PS> GetListValues Apple, Orange, Pear, Banana, Grapes, TooMuch

GetListValues : Cannot validate argument on parameter 'Columns'. 
The parameter requires at least 0 value(s) and no more than 5 value(s)
- 6 value(s) were provided.

A variant solution (requested later by the OP) that: 一种变体解决方案(OP稍后要求):

  • allows passing the max. 允许通过最大 number of columns as a parameter 列数作为参数

  • passes the column names as a single string with embedded quoting (eg, "'Apple', 'Orange', 'Pear', 'Banana', 'Grapes'" ). 将列名作为带有嵌入引号的单个字符串传递(例如, "'Apple', 'Orange', 'Pear', 'Banana', 'Grapes'" )。

function GetListValues {
  param(
    [string] $ColumnList,
    [int]    $MaxColumnCount
  )

  # Split something like "'Apple', 'Orange', 'Pear', 'Banana', 'Grapes'"
  # into an array of tokens.
  $Columns = $ColumnList -split "[, ']" -ne ''
  if ($Columns.Count -gt $MaxColumnCount) { Throw "Too many columns passed." }

  # Create an N-element array filled with the input column names
  # and 'Null' for any remaining elements.
  $allColumns = New-Object string[] $MaxColumnCount
  for ($i = 0; $i -lt $allColumns.Count; ++$i) {
    $allColumns[$i] = if ($i -lt $Columns.Count) { $Columns[$i] } else { 'Null' }
  }
  # Use string expansion (interpolation) to construct the output string.
  "Call db.Fruit($($allColumns -join ','))"
}

Example calls: 示例调用:

PS> GetListValues "'Apple', 'Orange', 'Pear', 'Banana', 'Grapes'" 5

Call db.Fruit(Apple,Orange,Pear,Banana,Grapes)

PS> GetListValues "" 3

Call db.Fruit(Null,Null,Null)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM