Dear Perl Monks,
I've looked at some posts here on a substring sort HERE and HERE which seem inapplicable to my case, but which do indeed present some of the difficulty of this sort (no pun intended) of task.
I'm needing to create a particular sort order for Biblical citations, based on the chronological order in which they would normally occur in the Bible. This order has no relationship to either numerical values nor to alphabetical values. Each reference must be sorted principally by the Book Title, but it must also include the chapter(s) and verse(s) (if present) which follow the book.
Here is a sample of the references needing to be sorted, and how I would hope it might look after being sorted.
| Biblical References | |
|---|---|
| UnSorted Input | Sorted Output |
|
|
Ideally, the sort should be done by the book first, and secondarily by its chapter/verse values. To begin with, I created a hash identifying each book and assigning it a numerical value for sort purposes. For now, I'm content with any permutation of the book reference having an equal value. A snippet follows.
sub byBiblicalBookOrder { my %sortdata = ( 'Genesis' => '100', 'Gen' => '100', 'Ge' => '100', 'Gn' => '100', 'GEN' => '100', 'GE' => '100', 'GN' => '100', 'GENESIS' => '100', 'Exodus' => '200', 'Exo' => '200', 'Ex' => '200', 'Exod' => '200', 'EXO' => '200', 'EX' => '200', 'EXOD' => '200', 'EXODUS' => '200', 'Leviticus' => '300', 'Lev' => '300', 'Le' => '300', 'Lv' => '300', 'LEV' => '300', 'LE' => '300', 'LV' => '300', 'LEVITICUS' => '300', ... 'Revelation' => '9000', 'Rev' => '9000', 'Re' => '9000', 'The Revelation' => '9000', 'Apocalypse' => '9000', 'Apoc' => '9000', 'REVELATION' => '9000', 'REV' => '9000', 'RE' => '9000', 'THE REVELATION' => '9000', 'APOCALYPSE' => '9000', 'APOC' => '9000' ); if ($sortdata{$a} > $sortdata{$b}) { return 1 } elsif ($sortdata{$b} > $sortdata{$a}) { return -1 } else { return 0 } } # END SUB byBiblicalBookOrder
But the problem is that perl's $a and $b also include extraneous book and chapter numbers for each reference, and therefore are not matched anywhere in the hash. To try to sort by the book names only, I tried calling the script like this:
print sort byBiblicalBookOrder map{/^(.*)(?>(?:\s.{1,5}(:\d+)*.*))/} @ +references;
...which didn't work. So far, anything I've tried either yields an alphabetical sort, a truncated sort (no chap/verse), or an unsorted result.
I wish this did not challenge me so much. It shows I still have sooo much to learn before I can feel I've really come close to proper utilization of the Perl language.
Your wisdom is much appreciated!
Blessings,
~Polyglot~
In reply to Regex Substring SORT Conundrum by Polyglot
| For: | Use: | ||
| & | & | ||
| < | < | ||
| > | > | ||
| [ | [ | ||
| ] | ] |