Ich habe eine riesige Musikwiedergabeliste und während einige Künstler viele Alben haben, haben andere nur einen Song. Ich wollte die Wiedergabeliste sortieren, damit derselbe Künstler nicht zweimal hintereinander abgespielt wird oder seine Songs meist am Anfang oder Ende der Wiedergabeliste landen.
Beispiel-Playlist:
$ cat /tmp/playlist.m3u
Anna A. - Song 1
Anna A. - Song 2
I--Rock - Song 1
John B. - Song 1
John B. - Song 2
John B. - Song 3
John B. - Song 4
John B. - Song 5
Kyle C. - Song 1
U--Rock - Song 1
Ausgabe von sort -R
oder shuf
:
$ sort -R /tmp/playlist.m3u
Anna A. - Song 1 #
U--Rock - Song 1
Anna A. - Song 2 # Anna's songs are all in the beginning.
John B. - Song 2
I--Rock - Song 1
John B. - Song 1
Kyle C. - Song 1
John B. - Song 4 #
John B. - Song 3 #
John B. - Song 5 # Three of John's songs in a row.
Was ich erwarte:
$ some_command /tmp/playlist.m3u
John B. - Song 1
Anna A. - Song 1
John B. - Song 2
I--Rock - Song 1
John B. - Song 3
Kyle C. - Song 1
Anna A. - Song 2
John B. - Song 4
U--Rock - Song 1
John B. - Song 5
text-processing
sort
random
Teresa und Junior
quelle
quelle
Antworten:
Wenn ich dieses Mischen auf ein Kartenspiel anwenden müsste, würde ich wahrscheinlich zuerst das Kartenspiel mischen und dann die Karten in einer Reihe vor meinen Augen anzeigen und von links nach rechts verarbeiten, wo immer sich benachbarte Clubs oder Herzen befinden. Englisch: www.mjfriendship.de/en/index.php?op...41&Itemid=32 Verschieben Sie alle bis auf einen zufällig an einen anderen Ort (wenn auch nicht neben einen anderen Typ).
Zum Beispiel mit einer Hand wie
Nach dem Grundmischen:
Für zwei Gruppen benachbarter Pik müssen wir 1, 2 und 3 verschieben. Für 1 stehen folgende Optionen zur Auswahl:
Wir wählen eine zufällig aus diesen 4 aus. Dann wiederholen wir den Vorgang für 2 und 3.
Umgesetzt
perl
wäre:Es wird eine Lösung mit nicht benachbarten Künstlern finden, wenn es existiert (es sei denn, mehr als die Hälfte der Songs sind vom selben Künstler) und sollte einheitlich AFAICT sein.
quelle
Ihre Beispieldaten und Einschränkungen lassen tatsächlich nur wenige Lösungen zu - Sie müssen beispielsweise John B. für jeden zweiten Song spielen. Ich gehe davon aus, dass es sich bei Ihrer tatsächlichen vollständigen Wiedergabeliste nicht im Wesentlichen um John B handelt .
Dies ist ein weiterer zufälliger Ansatz. Im Gegensatz zur @ frostschutz-Lösung läuft sie schnell. Es wird jedoch kein Ergebnis garantiert, das Ihren Kriterien entspricht. Ich präsentiere auch einen zweiten Ansatz, der mit Ihren Beispieldaten funktioniert - aber ich vermute, dass Ihre realen Daten zu schlechten Ergebnissen führen werden. Wenn Ihre realen Daten (verschleiert) vorliegen, füge ich Ansatz 3 hinzu. Dies ist ein einheitlicher Zufall, mit der Ausnahme, dass zwei Songs desselben Künstlers hintereinander vermieden werden. Beachten Sie, dass es nur 5 "Draws" in das "Deck" der verbleibenden Songs macht. Wenn es danach immer noch mit einem doppelten Interpreten konfrontiert wird, wird das Lied trotzdem ausgegeben - auf diese Weise wird garantiert, dass das Programm tatsächlich beendet wird.
Ansatz 1
Grundsätzlich wird an jedem Punkt eine Wiedergabeliste erstellt, in der gefragt wird, von welchen Künstlern ich noch nicht abgespielte Songs habe. Wählen Sie dann einen zufälligen Künstler und schließlich ein zufälliges Lied von diesem Künstler. (Das heißt, jeder Künstler wird gleich gewichtet, nicht proportional zur Anzahl der Songs.)
Probieren Sie Ihre eigentliche Wiedergabeliste aus und prüfen Sie, ob sie bessere Ergebnisse liefert als die gleichmäßig zufälligen.
Verwendung: Stellen
./script-file < input.m3u > output.m3u
Sie sicher, dasschmod +x
es selbstverständlich ist. Beachten Sie, dass die Signaturzeile, die sich oben in einigen M3U-Dateien befindet, nicht ordnungsgemäß verarbeitet wird. In Ihrem Beispiel war dies jedoch nicht der Fall.Ansatz 2
Als zweiter Ansatz, statt einen zufälligen Künstler auswählen , können Sie den Künstler mit den meisten Songs auswählen, die auch wir wählten nicht der letzte Künstler ist . Der letzte Absatz des Programms wird dann:
Der Rest des Programms bleibt gleich. Beachten Sie, dass dies bei weitem nicht die effizienteste Methode ist, aber für Wiedergabelisten jeder vernünftigen Größe schnell genug sein sollte. Mit Ihren Beispieldaten beginnen alle generierten Wiedergabelisten mit einem John B.-Song, einem Anna A.-Song und einem John B.-Song. Danach ist es viel weniger vorhersehbar (da außer John B. noch ein Song übrig ist). Beachten Sie, dass dies Perl 5.7 oder höher voraussetzt.
Ansatz 3
Die Verwendung ist die gleiche wie bei der vorherigen
0..4
Version. Sie könnten die Anzahl der Versuche erhöhen, z. B.0..9
insgesamt 10 geben. (0..4
=0, 1, 2, 3, 4
, Sie werden feststellen, dass es sich tatsächlich um 5 Artikel handelt).quelle
sed 's/ - .*//' output.m3u | uniq -d
). Und könntest du bitte erklären, ob es sich um Künstler handelt, die nicht am Anfang oder Ende der Wiedergabeliste landen?Wenn es Ihnen nichts ausmacht, schrecklich ineffizient zu sein ...
Es rollt einfach weiter und weiter, bis es zu einem Ergebnis kommt, das nicht zwei oder mehr Johns hintereinander hat. Wenn Ihre Wiedergabeliste so viele Johns enthält, dass eine solche Kombination nicht existiert oder äußerst unwahrscheinlich ist, hängt sie.
Beispielergebnis mit Ihrer Eingabe:
Wenn Sie die Debug-Zeilen auskommentieren, erfahren Sie, warum dies fehlgeschlagen ist:
Dies sollte helfen, die Ursache für den Fall zu bestimmen, dass es auf unbestimmte Zeit hängt.
quelle
sort
entworfen wurde.shuf
die Wiedergabeliste 80-mal schneller als gemischtsort -R
. Das wusste ich auch nicht! Ich lasse es 15 Minuten laufenshuf
, die Chancen stehen höher!echo "$D"
vor demif
. Das sollte Ihnen sagen, welche Duplikate die Auswahl des Ergebnisses verhindert haben. Das sollte Ihnen sagen, wo Sie nach dem Problem suchen müssen. (Edit: Möglicher Debug-Code zur Antwortsort
oder nicht wirklich möglichshuf
.Ein weiterer Ansatz mit Bash. Es liest die Wiedergabeliste in zufälliger Reihenfolge, versucht, die Zeile am anderen Ende der Liste einzufügen, wenn es sich um ein Duplikat handelt, und legt eine einzelne Kopie beiseite, um sie an einer anderen Stelle einzufügen. Es schlägt fehl, wenn es drei identische Duplikate gibt (erstes, letztes und beiseite gelegtes Duplikat), und diese fehlerhaften Einträge werden an das Ende der Liste angehängt. Es scheint in der Lage zu sein, die umfangreiche Liste zu lösen, die Sie die meiste Zeit hochgeladen haben.
Es könnte klüger sein ... in Ihrem John-Beispiel bleibt John normalerweise der letzte Künstler, weil er immer versucht, den ersten Künstler zuerst anzuhängen. Wenn es also zwei andere Künstler dazwischen gibt, ist es nicht klug genug, einen an den Anfang und den anderen an das Ende anzuhängen, um dem Dreifach-John auszuweichen. Bei Listen, bei denen grundsätzlich jeder andere Künstler John sein muss, kommt es also häufiger zu Fehlern, als Sie sollten.
quelle