KDB / Q: Wie schleife ich ohne Schleifen?

8

Ich lerne q über die kdb-Datenbank. Ich bin besorgt über die Tatsache, dass es keine Schleifen in q gibt. Ich muss einen Algorithmus schreiben, den ich mit mehreren geschachtelten for-Schleifen in einem ausführlichen Programm wie C schreiben würde. Aber in q bin ich fest davon, dass ich keine Schleife machen kann.

Nur um ein konkretes Beispiel zu geben (eines von vielen), habe ich diesen einfachen Vektor (Spaltentabelle):

%Vor%

Ich brauche einen Vektor, der 3by3 diese Einträge gruppiert, mit Überlagerung, wie (mit R-Syntax): Verschlüsse [0: 2], Verschlüsse [1: 3], Verschlüsse [2: 4], Verschlüsse [3: 5] ... Wie kann ich tun?

Im Allgemeinen, wie muss ich meine Mentalität ändern, um richtig in q zu programmieren?

Vielen Dank für Ihre Vorschläge Marco

    
Marco Mene 24.05.2013, 08:07
quelle

7 Antworten

8

Adressieren Sie Ihren letzten Punkt über "Wie muss ich meine Mentalität ändern, um richtig in q zu programmieren?":

Sie müssen über (/), scan (\) und .z.s statt Schleifen verwenden.

Zum Beispiel könnte Ihr Problem auf folgende Weise gelöst werden: (Beachten Sie, dass dies nicht die beste Lösung für Ihr spezielles Problem ist - Indexierung ist der bessere Ansatz dort - aber nichtsdestoweniger sollten diese Lösungen helfen, den Punkt zu verdeutlichen)

%Vor%

ie iterieren Sie über die Liste, hacken Sie jedes Mal eine davon ab, nehmen Sie die erste 3 jeder Iteration

oder ähnlich

%Vor%

d. rotieren Sie um das Achtfache, nehmen Sie die ersten 3 jeder Umdrehung

Verwendung eines .z.s Ansatzes

%Vor%

d. Wenn mindestens 3 Elemente übrig sind, nehmen Sie zuerst die 3, dann hacken Sie das erste Element ab und wenden Sie dieselbe Funktion erneut auf die verkürzte Liste an.

Die Verwendung von over (/) würde in diesem Beispiel verschachtelt werden, aber im Allgemeinen ist es sinnvoll, "while" -Typkonstrukte zu ersetzen

%Vor%

wird besser mit

erreicht %Vor%

d. addiere 10, zehn mal mit einem Startwert (Nullwert) von Null.

%Vor%

d. h. fügen Sie zufällige Zahlen zwischen 1 und 20 an, bis Sie 18 erreichen, und stoppen Sie dann.

wird besser mit

erreicht %Vor%

z. B. eine Zufallszahl zwischen 1 und 20 anhängen, iterieren, solange die Prüffunktion true zurückgibt, beginnend mit () als Startwert

Es gibt viele andere Optionen für die Verwendung von scan und over, abhängig davon, ob die Funktion, über die Sie iterieren, monadisch / diadisch usw. ist.

Als allgemeine Verallgemeinerung: eine Schleife vom Typ "for i = 1: 10" kann in q mit "function each i" erreicht werden, Eine Schleife vom Typ "do" kann in q mit "function / [numOfTimes; seed]" erreicht werden, Eine Schleife vom Typ "while" kann in q mit "function / [booleanCheckFunction; seed]"

erreicht werden     
terrylynch 01.08.2014 13:40
quelle
3

Q hat traditionelle Schleifenkonstrukte: do um eine Anweisung mehrmals zu wiederholen und < a href="http://code.kx.com/q/ref/control/#while"> während zu wiederholen, während eine gegebene Bedingung gilt. Darüber hinaus, q "Adverbien" jedes , über , usw. können Sie eine Funktion über Elemente eines Vektors" loopen ".

Um jedoch die Vorteile von q voll auszunutzen, sollten Sie lernen, explizite Schleifen zu vermeiden.

Vereinfachen Sie Ihr konkretes Beispiel (um einen einfachen Vektor anstatt einer einspaltigen Tabelle zu verwenden), hier können Sie einen Vektor von Preisen neu gruppieren:

%Vor%

So funktioniert es. (Denken Sie daran: q wird von rechts nach links ausgewertet.) Die Funktion prev verschiebt die Preise nach rechts der Vektor (vorangestellte Nullwerte am Anfang und Verwerfen des letzten Wertes:

%Vor%

Wir kombinieren den ursprünglichen Preisvektor mit zwei in einer $ 3 \ mal n $ -Matrix verschobenen. Die Spalten dieser Matrix sind die Gruppen, die wir wollen. Die Funktion flip transponiert die Matrix so, dass Sie die Gruppen als Zeilen erhalten und schließlich die ersten beiden löschen Zeilen, die Nullwerte enthalten, indem Sie den Operator _ verwenden.

    
Alexander Belopolsky 03.10.2015 00:43
quelle
3
%Vor%

Wie bereits erwähnt, ist die Verwendung von Built-Ins immer schneller als die Iteration mit 'oder /. Deshalb benötigt der Code aus der Top-Antwort für eine Million Elemente eine Ewigkeit, bis er vollständig ist und GBs Heap verwendet. Die Indizierung Methode von JPC und Harshal ist Meilen schneller, aber der Flip oben ist noch dreimal schneller.

Sobald Sie die Daten in dem Format haben, das Sie benötigen, verwenden Sie einfach jedes , um Ihre Schließung anzuwenden die Elemente der Liste.

Immer im Auge zu behalten, was Sie sagen, ist eine gute Übung - KDB wird nichts für Sie optimieren.

    
Alexander Balabin 11.06.2015 14:17
quelle
2

Was Nested Loops betrifft, habe ich herausgefunden, dass es nützlich ist, eine Kreuzliste zu erstellen. ZB

'für i = 1: 10

%Vor%

'

in q kannst du

%Vor%

wobei g als

definiert ist %Vor%

Hoffe das klärt auf. Was die Schließungen betrifft, so kennen sie dort die R-Syntax nicht. Kann helfen, wenn Sie sagen können, welche Ausgabe Sie wollen.

    
Naveen Sharma 24.05.2013 12:23
quelle
2

Eine Methode wäre, die Indizes, die Ihnen wichtig sind, zu berechnen und dann in das Array zu indizieren -

%Vor%     
MdSalih 24.05.2013 17:38
quelle
2

KDB Q ist eine Vektorverarbeitungssprache, ihre Stärke liegt in der Verarbeitung von Listen im Gegensatz zur Verarbeitung einzelner -Atome , wie sie regelmäßig in Imperativsprachen verwendet werden.

Wenn Ihnen das aber nicht bekannt ist, unterstützt Q Schleifen und kann in Fällen verwendet werden, in denen dies nicht anders aussieht! Hier ist ein Beispiel, das ich geschrieben hatte, als ich mit der Migration von Java zu KDB Q begann.

%Vor%

Es hat auch do-while kinda Syntax

%Vor%

Schauen Sie hier

nach     
Harshal Waghmare 25.07.2013 06:40
quelle
0

Wie einige der oben genannten Benutzer vorgeschlagen haben, denke ich, dass es am besten ist, hier die Indizes zu berechnen, die Sie wollen. Wenn möglich, vermeiden Sie lambdas und verwenden Sie Operatoren (es ist besser Stil).

%Vor%     
JPC 13.08.2013 20:52
quelle

Tags und Links