Jump to content

Possible to change order of lines in text file based on number?


Recommended Posts

So we start with this text in a txt file:

Objects (id: bounding-box centroid area mean-color):
  0: 280x80+0+0 140.8,39.4 20069 gray(0)
  4: 25x27+136+26 148.4,38.9 342 gray(255)
  5: 25x26+34+27 48.9,39.9 307 gray(255)
  6: 26x25+65+27 77.5,39.3 292 gray(255)
  11: 33x18+211+34 227.7,41.3 289 gray(255)
  9: 23x26+111+34 122.1,44.3 254 gray(255)
  7: 16x19+70+30 77.8,39.0 219 gray(0)
  2: 25x27+163+25 172.0,36.5 199 gray(255)
  10: 20x18+187+34 197.2,41.6 179 gray(255)
  3: 15x26+95+26 101.2,37.1 153 gray(255)
  13: 11x11+116+37 121.1,42.2 97 gray(0)

Then I run this script which I pierced together from 3 different threads on the forum. I know the code is ugly, but I don't know how to make it pretty. I'm happy and lucky to make something that works 😛

#include<file.au3>

$Filename = "results.txt"
;remove line 1
_FileWriteToLine($Filename, 1,"", 1)

Sleep (500)

$txt = FileRead("results.txt")
$out = "gray(0)"
$new = StringRegExpReplace($txt, '(?m)^.*\Q' & $out & '\E.*$', "")
FileWrite("new.txt", $new)

Sleep (500)

$sText = FileRead("new.txt")

$sText = StringRegExpReplace(StringRegExpReplace($sText, "(\v)+", @CRLF), "\A\v|\v\Z", "")

$hFile = FileOpen("NewText.txt", 2)
FileWrite($hFile, $sText)
FileClose($hFile)

This script does 3 things. It removes the 1st line in the text file. It removes each line that has the word "gray(0)" in it. And it removes all empty lines.

And I'm left with this:

4: 25x27+136+26 148.4,38.9 342 gray(255)
  5: 25x26+34+27 48.9,39.9 307 gray(255)
  6: 26x25+65+27 77.5,39.3 292 gray(255)
  11: 33x18+211+34 227.7,41.3 289 gray(255)
  9: 23x26+111+34 122.1,44.3 254 gray(255)
  2: 25x27+163+25 172.0,36.5 199 gray(255)
  10: 20x18+187+34 197.2,41.6 179 gray(255)
  3: 15x26+95+26 101.2,37.1 153 gray(255)

So far so good (except for my code being ugly).

What I need now is to change the order of these lines based on the first number in the middle of each line. Basically the number after the 25x27+136+26 on each line.

So the above would become below:

11: 33x18+211+34 227.7,41.3 289 gray(255)
  10: 20x18+187+34 197.2,41.6 179 gray(255)
  2: 25x27+163+25 172.0,36.5 199 gray(255)
  4: 25x27+136+26 148.4,38.9 342 gray(255)
  9: 23x26+111+34 122.1,44.3 254 gray(255)
  3: 15x26+95+26 101.2,37.1 153 gray(255)
  6: 26x25+65+27 77.5,39.3 292 gray(255)
  5: 25x26+34+27 48.9,39.9 307 gray(255)

As you can see, the lines are now aligned based on those middle numbers there - 227/197/172/148/122/101/77/48

 Not sure if AutoIT can do this or how simple it is. I guess the code would have to first locate the correct number on each line and get them all, and then compare them and align the lines correctly. Sounds a little far fetched, I don't know.

What say you guys?

Link to post
Share on other sites

Try and let us know how did it work for you 

#include <File.au3>
Local $a[0][5], $stxt = "NewText.txt"
_ArrayAdd($a, StringRegExpReplace(StringRegExpReplace(FileRead($stxt), "(?m)^\s+", ""), ' ', "|"))
For $i = 0 To UBound($a) - 1
    _ArraySwap($a, $i, _ArrayMaxIndex($a, 1, $i, -1, 2))
Next
ConsoleWrite(_ArrayToString($a, " ") & @LF)

 

Edited by Deye
Foot Print cleanup
Link to post
Share on other sites

Another way :

#include <File.au3>

example()

Func example()
  Local $aLine = FileReadToArray("Test.txt")  ; read the file and put it in an array
  Local $aFinal[0][3], $aTemp, $iCount
  For $i = 1 to UBound($aLine) - 1    ; skip first line
    If StringInStr($aLine[$i], "gray(0)") Then ContinueLoop   ; skip gray(0)
    $aTemp = StringRegExp($aLine[$i], "(\H+\h\H+\h)(\d+)(.*)", 1)  ; extract the 3 pieces of the line
    _ArrayAdd($aFinal, _ArrayToString($aTemp))   ; add the 3 pieces to a final array
    $aFinal[$iCount][1] = Number($aFinal[$iCount][1]) ; convert 2nd piece from string to number
    $iCount += 1
  Next
  _ArraySort($aFinal, 1, 0, 0, 1)  ; sort the final array based on that number
  _FileWriteFromArray("Sorted.txt", $aFinal, Default, Default, "") ; write the final array to a txt file
  _ArrayDisplay($aFinal)
EndFunc

ps.  maybe some code can be inelegant, but "ugly" not sure.  Overall, code is either working or is not working ;).  

Edited by Nine
Link to post
Share on other sites

For the fun :)

#Include <Array.au3>

$txt = "Objects (id: bounding-box centroid area mean-color):" & @crlf & _ 
    "  0: 280x80+0+0 140.8,39.4 20069 gray(0)" & @crlf & _ 
    "  4: 25x27+136+26 148.4,38.9 342 gray(255)" & @crlf & _ 
    "  5: 25x26+34+27 48.9,39.9 307 gray(255)" & @crlf & _ 
    "   " & @crlf & _ 
    "  6: 26x25+65+27 77.5,39.3 292 gray(255)" & @crlf & _ 
    "  11: 33x18+211+34 227.7,41.3 289 gray(255)" & @crlf & _ 
    "  9: 23x26+111+34 122.1,44.3 254 gray(255)" & @crlf & _ 
    "" & @crlf & _ 
    "  7: 16x19+70+30 77.8,39.0 219 gray(0)" & @crlf & _ 
    "  2: 25x27+163+25 172.0,36.5 199 gray(255)" & @crlf & _ 
    "  10: 20x18+187+34 197.2,41.6 179 gray(255)" & @crlf & _ 
    "  3: 15x26+95+26 101.2,37.1 153 gray(255)" & @crlf & _ 
    "  13: 11x11+116+37 121.1,42.2 97 gray(0)"

$txt = StringRegExpReplace($txt, '(^.+\R)|(?m)^(\s*\R)|(.*gray\(0\)\R?)', "")
$stmp = Execute("'" & StringRegExpReplace($txt, "(?m)(^.*?)(?<=\h)(\d+)(?=\.)", "' & StringFormat('%04i', '$2') & ' $1$2' & '") & "'")
$atmp = StringRegExp($stmp, '\N+', 3)
_ArraySort($atmp, 1)
$res = StringRegExpReplace(_ArrayToString($atmp, @crlf), '(?m)^\d{4}\h*', "")
Msgbox(0,"", $res)

 

Edited by mikell
completed
Link to post
Share on other sites

Another one

#Include <Array.au3>

$file = "results.txt"
$content = FileRead($file)

; removes first line, trailing spaces, lines containing 'gray(0)' and empty lines
$newContent = StringRegExpReplace($content, "(?x)(?m) \A\N+\R | ^\s+(.+gray\(0\)\N*(?:\R|$))? | ^\s*\R", "")

$aNumbers = StringRegExp($newContent, "([\d.]+),", 3)
For $i = 0 To UBound($aNumbers) - 1
    $aNumbers[$i] = Number($aNumbers[$i])
Next
_ArraySort($aNumbers)

Local $sOut
For $i = 0 To UBound($aNumbers) - 1
    $sOut &= ($i = 0 ? "" : @CRLF) & StringRegExp($newContent, "(?m)^(.+\Q" & $aNumbers[$i] & "\E(?:\.0)?,\N+)", 1)[0]
Next
ConsoleWrite($sOut)

 

Edited by jguinch
Link to post
Share on other sites

One more inspired by @jguinch

 

#include <File.au3>
Local $a[0][5], $stxt = "NewText.txt"
_ArrayAdd($a, StringRegExpReplace(StringRegExpReplace(FileRead($stxt), "(?m)^\s+", ""), ' ', "|"))
For $i = 0 To UBound($a) - 1
    $a[$i][2] = Number($a[$i][2])
Next
_ArraySort($a, 1, Default, Default, 2)
ConsoleWrite(_ArrayToString($a, " ") & @LF)

 

Edited by Deye
Link to post
Share on other sites

Scratching my head for a while on:

$stmp = Execute("'" & StringRegExpReplace($txt, "(?m)(^.*?)(?<=\h)(\d+)(?=\.)", "' & StringFormat('%04i', '$2') & ' $1$2' & '") & "'")

But after a while I understood what was happening 😉

 

Depending on expressiveness, flexibility and further needs I would probably do this in powershell

#$data=get-content result.txt -Encoding utf8

$data = @"
Objects (id: bounding-box centroid area mean-color):
  0: 280x80+0+0 140.8,39.4 20069 gray(0)
  4: 25x27+136+26 148.4,38.9 342 gray(255)
  5: 25x26+34+27 48.9,39.9 307 gray(255)
  6: 26x25+65+27 77.5,39.3 292 gray(255)
  11: 33x18+211+34 227.7,41.3 289 gray(255)
  9: 23x26+111+34 122.1,44.3 254 gray(255)
  7: 16x19+70+30 77.8,39.0 219 gray(0)
  2: 25x27+163+25 172.0,36.5 199 gray(255)
  10: 20x18+187+34 197.2,41.6 179 gray(255)
  3: 15x26+95+26 101.2,37.1 153 gray(255)
  13: 11x11+116+37 121.1,42.2 97 gray(0)
"@

$MyArrayList = [System.Collections.ArrayList]@()

#Lets first split it
$datalines=$data -split "`r`n" 

#Create the arraylist
foreach($dataline in $datalines) {
  $tline =$dataline.trimstart()
  $dataColumns=$tline.split(" ,")   

  $MyArrayList.add([pscustomobject]@{
    "dataline"          = $dataLine
    "id"                = $datacolumns[0]
    "boundingbox"       = $datacolumns[1]
    "centroid a"        = [double]$datacolumns[2]
    "centroid b"        = [double]$datacolumns[3]
    "area"              = $datacolumns[4]
    "meancolor"         = $datacolumns[5]
  }) 
} 

#Format, sort, filter, reshuffle
$myArraylist | format-table -autosize
$myArraylist | where meancolor -notin @('gray(0)','mean-color)') | sort "centroid a" -Descending | select dataline

Output

dataline                                    id  boundingbox  centroid a centroid b area  meancolor
--------                                    --  -----------  ---------- ---------- ----  ---------
  0: 280x80+0+0 140.8,39.4 20069 gray(0)    0:  280x80+0+0        140,8       39,4 20069 gray(0)  
  4: 25x27+136+26 148.4,38.9 342 gray(255)  4:  25x27+136+26      148,4       38,9 342   gray(255)
  5: 25x26+34+27 48.9,39.9 307 gray(255)    5:  25x26+34+27        48,9       39,9 307   gray(255)
  6: 26x25+65+27 77.5,39.3 292 gray(255)    6:  26x25+65+27        77,5       39,3 292   gray(255)
  11: 33x18+211+34 227.7,41.3 289 gray(255) 11: 33x18+211+34      227,7       41,3 289   gray(255)
  9: 23x26+111+34 122.1,44.3 254 gray(255)  9:  23x26+111+34      122,1       44,3 254   gray(255)
  7: 16x19+70+30 77.8,39.0 219 gray(0)      7:  16x19+70+30        77,8         39 219   gray(0)  
  2: 25x27+163+25 172.0,36.5 199 gray(255)  2:  25x27+163+25        172       36,5 199   gray(255)
  10: 20x18+187+34 197.2,41.6 179 gray(255) 10: 20x18+187+34      197,2       41,6 179   gray(255)
  3: 15x26+95+26 101.2,37.1 153 gray(255)   3:  15x26+95+26       101,2       37,1 153   gray(255)
  13: 11x11+116+37 121.1,42.2 97 gray(0)    13: 11x11+116+37      121,1       42,2 97    gray(0)  



dataline                                   
--------                                   
  11: 33x18+211+34 227.7,41.3 289 gray(255)
  10: 20x18+187+34 197.2,41.6 179 gray(255)
  2: 25x27+163+25 172.0,36.5 199 gray(255) 
  4: 25x27+136+26 148.4,38.9 342 gray(255) 
  9: 23x26+111+34 122.1,44.3 254 gray(255) 
  3: 15x26+95+26 101.2,37.1 153 gray(255)  
  6: 26x25+65+27 77.5,39.3 292 gray(255)   
  5: 25x26+34+27 48.9,39.9 307 gray(255)

 

Link to post
Share on other sites
  • 4 weeks later...

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
  • Recently Browsing   0 members

    No registered users viewing this page.

×
×
  • Create New...