29

I want to make a PowerShell script that takes each file of my music library and then does a hash sum of it and writes that into a file like so:

test.txt ; 131 136 80 89 119 17 60 123 210 121 188 42 136 200 131 198

When I start the script, I need it to first compare my music library with the already existing values, but for this I just want to cut off everything after the ; so that it can compare filename against filename (or filepath)... but I'm stumped at how to do that.

I tried replacing the value via $name = $name -replace ";*","", but that didn't work. I also tried to filter... but I don't know how.

TylerH
  • 20,799
  • 66
  • 75
  • 101
DemonWareXT
  • 471
  • 2
  • 7
  • 16

7 Answers7

71
$pos = $name.IndexOf(";")
$leftPart = $name.Substring(0, $pos)
$rightPart = $name.Substring($pos+1)

Internally, PowerShell uses the String class.

VVS
  • 19,405
  • 5
  • 46
  • 65
20
$text = "test.txt ; 131 136 80 89 119 17 60 123 210 121 188 42 136 200 131 198"

$text.split(';')[1].split(' ')
Alexander Vogt
  • 17,879
  • 13
  • 52
  • 68
Sarang
  • 641
  • 1
  • 9
  • 12
9

You can use a Split :

$text = "test.txt ; 131 136 80 89 119 17 60 123 210 121 188 42 136 200 131 198"
$separator = ";" # you can put many separator like this "; : ,"

$parts = $text.split($separator)

echo $parts[0] # return test.txt
echo $parts[1] # return the part after the separator
hdoghmen
  • 3,175
  • 4
  • 29
  • 33
2

$name -replace ";*",""

You were close, but you used the syntax of a wildcard expresson rather than a regular expression, which is what the -replace operator expects.

Therefore (hash sequence shortened):

PS> 'test.txt ; 131 136 80 89 119 17 60 123 210 121 188' -replace '\s*;.*'
test.txt

Note:

  • Omitting the substitution-text operand (the 2nd RHS operand) implicitly uses "" (the empty string), i.e. it effectively removes what the regex matched.

  • .* is what represents a potentially empty run (*) of characters (.) in a regex - it is the regex equivalent of * by itself in a wildcard expression.

  • Adding \s* before the ; in the regex also removes trailing whitespace (\s) after the filename.

  • I've used '...' rather than "..." to enclose the regex, so as to prevent confusion between what PowerShell expands up front (see expandable strings in PowerShell and what the .NET regex engine sees.

mklement0
  • 382,024
  • 64
  • 607
  • 775
1

This does work for a specific delimiter for a specific amount of characters between the delimiter. I had many issues attempting to use this in a for each loop where the position changed but the delimiter was the same. For example I was using the backslash as the delimiter and wanted to only use everything to the right of the backslash. The issue was that once the position was defined (71 characters from the beginning) it would use $pos as 71 every time regardless of where the delimiter actually was in the script. I found another method of using a delimiter and .split to break things up then used the split variable to call the sections For instance the first section was $variable[0] and the second section was $variable[1].

David
  • 11
  • 1
0

I had a dir full of files including some that were named invoice no-product no.pdf and wanted to sort these by product no, so...

get-childitem *.pdf | sort-object -property @{expression={$\_.name.substring($\_.name.indexof("-")+1)}}

Note that in the absence of a - this sorts by $_.name

henrycarteruk
  • 12,708
  • 2
  • 36
  • 40
Clarius
  • 1,183
  • 10
  • 10
0

Using regex, the result is in $matches[1]:

$str = "test.txt ; 131 136 80 89 119 17 60 123 210 121 188 42 136 200 131 198"
$str -match "^(.*?)\s\;"
$matches[1]
test.txt