Schreiben Sie eine Funktion oder ein Programm, das eine Liste aufnimmt und eine Liste der lokalen Extreme erstellt.
In einer Liste ist [x_0, x_1, x_2...]
ein lokales Extrem ein x_i
solches x_(i-1) < x_i
und x_(i+1) < x_i
oder x_(i-1) > x_i
und x_(i+1) > x_i
. Beachten Sie, dass das erste und letzte Element der Liste niemals lokale Extreme sein können.
Also für einige Beispiele
local_extremes([1, 2, 1]) = [2]
local_extremes([0, 1, 0, 1, 0]) = [1, 0, 1]
local_extremems([]) = []
Dies ist Codegolf, also gewinnt der kürzeste Code!
1 2 2 1
sollten diese nicht2
auch als Extreme betrachtet werden? - Ich weiß, dies würde die Lösung viel schwieriger machen ...Antworten:
Mathematica
66 5851Aktuelle Lösung
Verkürzt durch einen Beitrag von Calle.
Partition[#,3,1]
findet die dreifachen.(a-b) (b-c)<0
wenn wahr ist , und nur dann , wennb
untera
,c
oder übera
,c
. und schaut auf nimmt die Anzeichen der Unterschiede. Ein lokales Extrem wird entweder{-1,1}
oder zurückkehren{1,-1}
.Beispiele
Frühere Lösung
Dies sieht beispielhaft alle Tripel (generiert von
Partition
) aus und bestimmt, ob das mittlere Element kleiner als beide Extreme oder größer als die Extreme ist.Erste Lösung
Dies findet die Dreiergruppen und nimmt die Anzeichen der Unterschiede wahr. Ein lokales Extrem wird entweder
{-1,1}
oder zurückkehren{1,-1}
.Beispiel
Analyse :
%
verweist auf das Ergebnis aus der jeweils vorhergehenden Zeile.Sort@Sign@Differences@x=={-1,1}
identifiziert die Tripel aus {{9, 10, 7}, {10, 7, 6}, {7, 6, 9}, {6, 9, 0}, {9, 0, 3}, {0, 3}. 3}, {3, 3, 1}, {3, 1, 10}}, so dass das Vorzeichen (-, 0, +) der Differenzen aus a-1
und a besteht1
. Im vorliegenden Fall sind dies:Für jeden dieser Fälle
x[[2]]
bezieht sich x auf den zweiten Term. Dies sind alle lokalen Maxima und Minima.quelle
J - 19 char
Konnte nicht helfen;)
Erklärung folgt:
2-/\]
- Über jedes Elementpaar im Argument (jedes 2-Item-Long-Infix) den Unterschied ziehen.2*/\
- Nehmen Sie nun über jedes Paar der neuen Liste das Produkt.0>
- Prüfen Sie, ob jedes Ergebnis kleiner als 0 ist. Dies geschieht nur, wenn die Multiplikanden alternierende Vorzeichen hatten, dh nicht, wenn sie dasselbe Vorzeichen hatten oder eines von beiden Null war.0,
- Deklarieren Sie, dass das erste Element kein extremes Element ist.}:
- Schneiden Sie das letzte Element ab, denn das kann auch kein Extrem sein.#~
- Verwenden Sie die wahren Werte auf der rechten Seite, um Elemente aus der Liste auf der linken Seite auszuwählen.Verwendung:
quelle
Javascript -
6245 ZeichenBearbeiten
quelle
Ruby,
8370605549 ZeichenGibt alle lokalen Extreme in STDOUT aus.
Benutzt den<=>
"Raumschiff" -Operator, den ich wirklich mag. (Es gibt 1 zurück, wenn das erste Ding größer als das zweite ist, -1, wenn es kleiner ist, und 0, wenn es gleich ist. Wenn sie also zu -2 oder 2 addieren, bedeutet das, dass die Mitte ein Extrem ist.)Nicht mehr, da @daniero darauf hingewiesen hat, dass der "offensichtliche" Weg tatsächlich kürzer ist!Schon wieder geändert! Jetzt wird der fantastische Algorithmus verwendet, der in MT0s Antwort enthalten ist (+1 für ihn!).
Außerdem gefällt mir,
each_cons
welchen
Gruppen von aufeinanderfolgenden Elementen in einem Array ausgewählt werden. Und das Schleppenif
ist auch interessant.Insgesamt gefällt mir, wie elegant es aussieht.
Einige Probeläufe:
quelle
f=->a{a.each_cons(3){|x,y,z|p y if((x<=>y)+(z<=>y)).abs==2}}
x>y&&y<z||x<y&&y>z
(auch wenn der Raumschiffbetreiber sehr hübsch ist);)!((x..z)===y)
ist noch kürzer, wenn auch nicht so schlaux < z
.C ++ - 208 Zeichen
Wieder die längste Lösung:
Geben Sie zur Verwendung Ihre ganzen Zahlen und dann ein beliebiges Zeichen ein, das den Eingabestream zum Absturz bringt. Alle Zeichen, die keine Zahlen sind, sollten funktionieren.
Eingang:
0 1 0 x
Ausgabe:
1
quelle
deque
anstelle von a verwendenvector
, um 2 Zeichen zu erhalten.i
und zu verwendenj
, können Sie auchint i;
direkt nach der Sammlung deklarieren und in den beiden Schleifen verwenden, anstatt zwei Variablen zu deklarieren.i++
in Ihrer for-Schleife loswerden und Ihre Bedingung mit beginnenif(v[++i]>[i-1]...
, um wieder ein Zeichen zu erhalten.Matlab - 45 Bytes
quelle
Python 2.7 - 73 Bytes
Nicht zu beeindruckend (Sehen Sie sich jedes Element der Liste mit Ausnahme des ersten und des letzten an, um festzustellen, ob es größer oder kleiner als die Nachbarn ist).
Ich poste es meistens nur, weil nicht jeder weiß, dass Sie es tunx<y>z
und funktionieren lassen können. Ich finde das irgendwie ordentlich.Ja,
x<y>z
ist eine coole Funktion von Python, aber in diesem Fall nicht optimal. Vielen Dank an VX für den Multiplikationstrick, der mir überhaupt nicht eingefallen ist. Wrzlprmft erinnerte mich daran, dass das Deklarieren einer anonymen Funktion weniger Tastenanschläge als istdef x(y):
.quelle
if(l[i]-l[i-1])*(l[i]-l[i+1])>0
würde den Code um 11 Zeichen reduzieren ...def e(l):\n
die gleiche Anzahl von Zeichen wiee=lambda l:
, aber ich habe vergessen, dass Sie dasreturn
Schlüsselwort nicht verwenden müssen, verblüfft. Vielen Dank!(l[i]-l[i-1])*(l[i]-l[i+1])
ist ,1
wennl[i]
ein lokales Extrem ist und0
sonst brauche ich nicht zu verwenden>0
. Ich kann Python einfach als Bool interpretieren lassen. :)\n
in der Deklaration überhaupt nicht benötigt ! Das hätte zwei Zeichen gespart, aber die Einbeziehung vonreturn
macht es immer noch nicht wert.Haskell 50
quelle
x>p&&x>n
hat einen Charakter weniger alsx>max p n
:-),
ist ebenfalls nicht erforderlich.x>p&&x>n
an(x>p)==(x>n)
für lokale Minima zu fügt 4 weitere Zeichen.Gelee , 8 Bytes
Probieren Sie es online!
Erläuterung
Ein Element ist nur dann ein lokales Extrem, wenn sein Unterschied zum linken Nachbarn ein entgegengesetztes Vorzeichen zu seinem Unterschied zum rechten Nachbarn hat, dh die Vorzeichen der Unterschiede unterscheiden sich um 2 oder -2. Jelly hat eine Reihe nützlicher Grundelemente für den Umgang mit "Elementen mit bestimmten Eigenschaften suchen" (insbesondere können wir Elemente mit bestimmten Eigenschaften in einer Liste suchen und diese verwenden, um Elemente aus einer anderen Liste zu extrahieren), was bedeutet, dass wir zurückübersetzen können die ursprüngliche Liste mehr oder weniger direkt (wir müssen nur um 1 versetzen, weil das erste und das letzte Element der ursprünglichen Liste bei der Differenzbildung verloren gegangen sind).
quelle
Python mit Numpy -
81 7467 Bytes (6154 ohne dieimport
Linie)Die Eingabe muss ein Numpy-Array sein.
quelle
C 83
quelle
awk - 32 Zeichen
Keine Hoffnung, eine Sprache wie J oder APL wegen der Kürze zu schlagen, aber ich dachte, ich würde trotzdem meinen Hut in den Ring werfen. Erläuterung:
a
,b
, undc
hältx_i
,x_(i-1)
undx_(i-2)
b-c
unda-b
approximiere die Ableitung davor und danachx_(i-1)
x_(i-1)
handelt es sich um ein lokales Extrem, also drucken Siequelle
Brachylog , 17 Bytes
Probieren Sie es online!
Übernimmt die Eingabe über die Eingabevariable und generiert die Ausgabe über die Ausgabevariable.
Wenn garantiert werden kann, dass Werteläufe fehlen, werden
s₃{{⌉|⌋}.&bh}
vier Bytes eingespart.quelle
Perl 5
-p
, 49 BytesProbieren Sie es online!
quelle
Wolfram Language (Mathematica) ,
4342 BytesProbieren Sie es online!
Ich denke,
Nothing
ist zu lang ...quelle
05AB1E ,
1110 BytesProbieren Sie es online aus oder überprüfen Sie ein paar weitere Testfälle .
Erläuterung:
quelle
PHP,
116 114113Anwendungsbeispiel:
quelle
Haskell, 70 ° C
Golf Version
Ungolfed-Version
quelle
Javascript: 102 Zeichen
quelle
APL, 19 Bytes
Ich habe die 20-Zeichen-J-Version in APL konvertiert. Aber ich füge am Anfang und am Ende eine Null hinzu, anstatt die erste und die letzte Ziffer zu entfernen. Ansonsten funktioniert es genauso wie die J-Version.
⍵
- Formalparameter Omega. Dies ist die Eingabe für die Funktion.quelle
{x@1+&0>2_*':-':0 0,x}
. 6 dieser Zeichen (2_
und0 0,
) werden zum Schutz vor einem Längenfehler ausgegeben, wenn das Argument kürzer als zwei Elemente ist. Wäre dies nicht der Fall, wären es 16 ... Die Aktion ist auch etwas anders - wir müssen die drehen Boolesche Liste in eine Liste von Indizes mit1+&
und verwenden Sie diese, umx
erneut zu indizieren - aber es ist kürzer und auch eine sehr k-ische Sache, die zu tun ist.Python 2 , 59 Bytes
Probieren Sie es online!
Diese Funktion vermeidet meist das teure Indizieren, indem die Elemente der Liste anstelle der Liste selbst als Argumente verwendet werden. Während die Liste mehr als ein Element enthält, wird die Liste rekursiv aufgebaut und bei jedem Schritt auf ein Maximum geprüft.
quelle