mIRC Homepage
Posted By: Shanatan Filtering/sorting hashtable? - 14/03/16 06:47 PM
Could anyone give me some pointers of how to filter/sort the data in a hashtable in a descending/ascending order?

So like:
name1 (1000), name2 (900), name3 (800), etc etc

And conversely:
name4(-100), name5 (0), name6 (100), etc etc

In a nutshell, a top10 and a bottom10. Can I just throw the filter function over a hashtable?
Posted By: Dazuz Re: Filtering/sorting hashtable? - 14/03/16 07:08 PM
Code:
;This is here just so we can get a hash table with some data in it.
alias randomstuff {
  hfree -w randomstuff
  hmake randomstuff
  var %x = 5000
  while (%x) {
    hadd randomstuff %x %x
    dec %x
  }
}

alias sortrandomstuff {

  ;Window to sort and list the items/data.
  window -n @randomstuff
  clear @randomstuff

  ;List all the items and data in the hash table.
  noop $hfind(randomstuff,*,0,w,aline @randomstuff $1 $hget(randomstuff,$1))

  ;"u" makes it numerical sort. If you want it in descending order, add "e" flag.
  ;2 is the column and 32 is the character, it's same as with gettok.
  filter -cwwtu 2 32 @randomstuff @randomstuff

  ;Activates the window after listing's done. (You really want to hide lists/windows/whatever when listing loads of lines.)
  window -a @randomstuff
}


/help $line
/help /filter
/help /window
Posted By: Shanatan Re: Filtering/sorting hashtable? - 14/03/16 07:44 PM
Thanks, but I figured it out myself in the meanwhile. I didn't think of just saving the hashtable to a file and throwing filter over it.

Code:
alias top10 {
  hsave -no points top10.txt
  filter -ffcteun 1 32 top10.txt top10.txt
  var %i = 1 | while (%i <= 10) {
    var %top10.item = $hget(points,$gettok($read(top10.txt,nt,%i),1,32)).item
    set %top10 %top10 %top10.item  ( $+ $hget(points,%top10.item) $+ )
    inc %i
  }
  echo $replace(%top10,$chr(32),$+($chr(44),$chr(32)))
  unset %top10
}

alias bottom10 {
  hsave -no points bottom10.txt
  filter -ffctun 1 32 bottom10.txt bottom10.txt
  var %i = 1 | while (%i <= 10) {
    var %bottom10.item = $hget(points,$gettok($read(bottom10.txt,nt,%i),1,32)).item
    set %bottom10 %bottom10 %bottom10.item ( $+ $hget(points,%bottom10.item) $+ )
    inc %i
  }
  echo $replace(%bottom10,$chr(32),$+($chr(44),$chr(32)))
  unset %bottom10
}


That seems to work how I want it to.
Posted By: Dazuz Re: Filtering/sorting hashtable? - 14/03/16 08:57 PM
First of all, it's a really bad idea to use $read multiple times in one alias, especially if you can get around it.

Secondly, you can add whatever separators you want when you're forming the list.

I'll use my own example to get around that $read problem:
Code:
alias sortrandomstuff {
  window -h @randomstuff
  clear @randomstuff
  noop $hfind(randomstuff,*,0,w,aline @randomstuff $1 $hget(randomstuff,$1))
  filter -cwwtu 2 32 @randomstuff @randomstuff
  var %x = 1,%l
  while (%x <= 10) {

    ;$hfind formatted the lines as follows: name<space>score
    ;$1 = users name & $2 = score
    tokenize 32 $line(@randomstuff,%x)

    ;And here the magic happens.
    ;There's multiple ways to do it, and this is one of them.
    ;It separates the entries with $chr(1) which are replaced with comma and space when we're done.
    var %l = $addtok(%l,Amazing user $1 has $2 points and is ranked $ord(%x),1)
    inc %x
  }
  window -c @randomstuff

  ;Here we replace $chr(1) with whatever we want.
  echo -a $replacex(%l,$chr(1),$chr(44) $+ $chr(32))
}
Posted By: FroggieDaFrog Re: Filtering/sorting hashtable? - 15/03/16 12:52 AM
Q: what command are you using to store the values?


Code:
/hadd -m table username points
??
Posted By: Shanatan Re: Filtering/sorting hashtable? - 15/03/16 02:19 AM
Minus the 'm' switch, yes.
© mIRC Discussion Forums