Make text and highlight in Windows Powershell (or dotNet aka.net)

Background

Python has "textwrap" and "dedent" functions. They do almost what you would expect from whatever string you supply.

textwrap.wrap (text [, width [, ...]])

Wraps one paragraph in text (line), so each line is at most characters wide. Returns a list of output lines without a trailing newline.

textwrap.dedent (text)

Remove all common spaces from every line in the text.

http://docs.python.org/library/textwrap.html

Question:

How do you do this in Windows PowerShell (or using the .NET methods you call from PowerShell)?

+2


source to share


3 answers


This is sloppy code ...



#requires -version 2.0
    function wrap( [string]$text, [int]$width ) {
    $i=0;
    $text.ToCharArray() | group { [Math]::Floor($i/$width); (gv i).Value++ } | % { -join $_.Group }
}

function dedent( [string[]]$text ) {
    $i = $text | % { $_ -match "^(\s*)" | Out-Null ; $Matches[1].Length } | sort | select -First 1
    $text -replace "^\s{$i}"
}

      

+3


source


I think you should create a CLI utility with this behavior and customize it as you see fit. And then just use it as a command in your shell. You may need to add your script to PATH as well.



+1


source


Looking at the results in python at http://try-python.mired.org/ , it seems that the correct algorithm breaks at word boundaries, instead of substring lengths from the text.

function wrap( [string]$text, [int]$width = 70 ) {
  $line = ''

  # Split the text into words.
  $text.Split( ' '.ToCharArray( ) ) | % {
    # Initialize the first line with the first word.
    if( -not $line ) { $line = $_ }
    else {
      # For each new word, try to add it to the current line.
      $next = $line + ' ' + $_

      # If the new word goes over the limit,
      #  return the last line and start a new one.
      if( $next.Length -ge $width ) { $line; $line = $_ }
      # Otherwise, use the updated line with the new word.
      else { $line = $next }
    }
  }

  # Return the last line, containing the remainder of the text.
  $line
}

      

And here is an alternative implementation for dedent

.

function dedent( [string[]]$lines ) {
  # Find the shortest length of leading whitespace common to all lines.
  $commonLength = (
    $lines | % {
      $i = 0
      while( $i -lt $_.Length -and [char]::IsWhitespace( $_, $i ) ) { ++$i }
      $i
    } | Measure-Object -minimum
  ).Minimum

  # Remove the common whitespace from each string
  $lines | % { $_.Substring( $commonLength ) }
}

      

Hopefully their more verbosity will provide better clarity :)

+1


source







All Articles