;
À titre d'exemple adapté du rapport technique susmentionné, supposons que l'on vous donne une table dbo.Ticker, avec le symbole des colonnes, la date de transaction et le prix. Utilisez le code suivant pour créer la table, la remplir avec des exemples de données et l'interroger :
SET NOCOUNT ON ; UTILISER tempdb ; SUPPRIMER LA TABLE SI EXISTE dbo.Ticker ; CREATE TABLE dbo.Ticker( symbole VARCHAR(10) NOT NULL, tradedate DATE NOT NULL, price NUMERIC(12, 2) NOT NULL, CONTRAINTE PK_Ticker PRIMARY KEY (symbole, tradedate));GO INSERT INTO dbo.Ticker(symbol, tradedate , prix) VALEURS ('STOCK1', '20190212', 150.00), ('STOCK1', '20190213', 151.00), ('STOCK1', '20190214', 148.00), ('STOCK1', '20190215', 146.00 ), ('STOCK1', '20190218', 142.00), ('STOCK1', '20190219', 144.00), ('STOCK1', '20190220', 152.00), ('STOCK1', '20190221', 152.00), ('STOCK1', '20190222', 153.00), ('STOCK1', '20190225', 154.00), ('STOCK1', '20190226', 154.00), ('STOCK1', '20190227', 154.00), (' STOCK1', '20190228', 153.00), ('STOCK1', '20190301', 145.00), ('STOCK1', '20190304', 140.00), ('STOCK1', '20190305', 142.00), ('STOCK1' , '20190306', 143.00), ('STOCK1', '20190307', 142.00), ('STOCK1', '20190308', 140.00), ('STOCK1', '20190311', 138.00), ('STOCK2', ' 20190212', 330.00), ('STOCK2', '20190213', 329.00), ('STOCK2', '20190214', 329.00), ('STOCK2', '20190215', 326.00), ('STOCK2', '20190218', 325.00), ('STOCK2', '20190219', 326.00), ('STOCK2', '20190220', 328.00) , ('STOCK2', '20190221', 326.00), ('STOCK2', '20190222', 320.00), ('STOCK2', '20190225', 317.00), ('STOCK2', '20190226', 319.00), ( 'STOCK2', '20190227', 325.00), ('STOCK2', '20190228', 322.00), ('STOCK2', '20190301', 324.00), ('STOCK2', '20190304', 321.00), ('STOCK2 ', '20190305', 319.00), ('STOCK2', '20190306', 322.00), ('STOCK2', '20190307', 326.00), ('STOCK2', '20190308', 326.00), ('STOCK2', '20190311', 324.00); SELECT symbole, date de transaction, prix FROM dbo.Ticker ;
Ce code génère la sortie suivante :
symbol tradedate price------ ---------- ------ STOCK1 2019-02-12 150.00STOCK1 2019-02-13 151.00STOCK1 2019-02-14 148.00STOCK1 2019-02-15 146.00stock1 2019-02-18 142.00stock1 2019-02-19 144.00stock1 2019-02-20 152.00stock1 2019-02-21 152.00stock1 2019-02-22 153.00stock1 2019-02-25 154.00stock1 2019 2019 -02-26 154.00STOCK1 2019-02-27 154.00STOCK1 2019-02-28 153.00STOCK1 2019-03-01 145.00STOCK1 2019-03-04 140.00STOCK1 2019-03-05 142.00STOCK1 2019-03-04 142.00STOCK1 2019-03-04 142.00STOCK1 2019-03-04 03-07 142.00Stock1 2019-03-08 140.00STOCK1 2019-03-11 138.00STOCK2 2019-02-12 330.00STOCK2 2019-02-13 329.00STOCK2 2019-02-14 329.00Stock2 2019-02-15 326.00STOCK2 2019-02 -18 325.00STOCK2 2019-02-19 326.00STOCK2 2019-02-20 328.00STOCK2 2019-02-21 326.00STOCK2 2019-02-22 320.00STOCK2 2019-02-25 2016STOCK2 2019-02-25 317.00STOCK2 2019-02-25 2016STOCK2 2019-02-22 27 325.00STOCK2 2019-02-28 322.00STOCK2 2019-03-01 324.00STOCK2 2019-03-04 321.00STOCK2 2019-03-05 319.00STOCK2 2019-03-06 322.00STOCK2 2019-03-07 326.00STOCK2 2019-03-08 326.00STOCK2 2019-03-11 324.0040 ligne(s) affectée(s).
La requête suivante identifie les modèles représentant des formes en V dans le cours de l'action (une période avec un prix strictement décroissant suivie d'une période avec un prix strictement croissant), en utilisant ONE ROW PER MATCH comme lignes de modèle de ligne par correspondance choix :
SELECT MR.symbol, MR.matchnum, MR.startdate, MR.startprice, MR.bottomdate, MR.bottomprice, MR.enddate, MR.endprice, MR.maxpriceFROM dbo.Ticker MATCH_RECOGNIZE (PARTITION BY symbole ORDER BY tradedate MEASURES MATCH_NUMBER() AS matchnum, A.tradedate AS startdate, A.price AS startprice, LAST(B.tradedate) AS bottomdate, LAST(B.price) AS bottomprice, LAST(C.tradedate) AS enddate, -- identique à LAST(tradedate) LAST(C.price) AS endprice, MAX(U.price) AS maxprice -- identique à MAX(price) ONE ROW PER MATCH -- default AFTER MATCH SKIP PAST LAST ROW -- default PATTERN (A B+ C+ ) SUBSET U =(A, B, C) DEFINE -- A par défaut à True, correspond à n'importe quelle ligne, identique à la définition explicite de A AS 1 =1 B AS B.price PREV(C.price) ) AS MR;
La clause PARTITION BY définit que vous souhaitez gérer chaque symbole boursier séparément.
La clause ORDER BY définit l'ordre en fonction de la date de transaction.
La clause DEFINE définit des variables de modèle de ligne représentant les différentes sous-séquences de lignes dans le modèle. Dans l'exemple ci-dessus, A représente n'importe quelle ligne comme point de départ, B représente une sous-séquence de prix décroissants (B.price PREV( C.prix)).
La clause PATTERN utilise des expressions régulières pour identifier un modèle. Dans la requête ci-dessus, le modèle est (A B+ C+), c'est-à-dire (n'importe quelle ligne, suivie d'une ou plusieurs lignes avec des prix décroissants, suivies d'une ou plusieurs lignes avec des prix croissants). Voici les quantificateurs de modèle d'expression régulière que vous pouvez utiliser :
* — zéro (0) correspondance ou plus+ — une (1) correspondance ou plus ? — aucune correspondance ou une (1) correspondance, facultatif{ n } — exactement n correspondances{ n, } — n correspondances ou plus{ n, m } — entre n et m correspondances (inclusives){ , m } — entre zéro (0 ) et m (inclusive) matches{- Variable -}, par exemple, {- A -} — indique que les lignes correspondantes doivent être exclues de la sortie (utile uniquement si ALL ROW PER MATCH spécifié)|, par exemple, A | B — alternance(), par exemple, (A | B) — groupement^, par exemple, ^A{1, 3} — début d'un motif de ligne partition$, par exemple, A{1, 3}$ — fin d'un motif de ligne partitionner
Par défaut, les quantificateurs sont gourmands, mais vous pouvez les définir comme réticents.
La clause SUBSET vous permet de définir une liste de sous-ensemble nommé de variables.
La clause MEASURES définit les mesures liées au modèle. Vous pouvez appliquer des calculs à des variables de modèle et à des sous-ensembles. La fonction MATCH_NUMBER() attribue des entiers séquentiels commençant par 1 pour les correspondances au sein de la partition. Vous pouvez utiliser des opérations telles que FIRST, LAST, PREV et NEXT, ainsi que des calculs agrégés.
Cette requête utilise ONE ROW PER MATCH comme option de lignes de modèle de ligne par correspondance. Cela signifie que le tableau de résultats aura une ligne par correspondance de modèle, similaire au résultat du regroupement. L'alternative est TOUTES LES LIGNES PAR CORRESPONDANCE où vous voulez que les lignes de détail soient renvoyées par correspondance de modèle (exemple à suivre sous peu).
Cette requête utilise AFTER MATCH SKIP PAST LAST ROW comme AFTER MATCH . Cela signifie qu'une fois qu'une correspondance est trouvée, vous voulez que la prochaine tentative commence après la dernière ligne de la correspondance actuelle. Il existe d'autres alternatives comme rechercher la correspondance suivante dans la ligne suivant la première ligne de la correspondance actuelle (PASSER À LA LIGNE SUIVANTE), ou passer à une position relative à une variable de modèle de ligne.
Voici le résultat attendu de cette requête :
symbol matchnum startdate startprice bottomdat bottomprice enddate endprice maxprice------ -------- ---------- ---------- ---- ------ ----------- ---------- -------- --------STOCK1 1 2019-02-13 151,00 2019-02-18 142.00 2019-02-20 152.00 152.00stock1 2 2019-02-27 154,00 2019-03-04 140,00 2019-03-06 143,00 154.00stock2 1 2019-02-14 329.00 2019-02-18 325.00 2019 -02-20 328.00 329.00STOCK2 2 2019-02-21 326.00 2019-02-25 317.00 2019-02-27 325.00 326.00STOCK2 3 2019-03-01 324.00 2019-03-05 319.00 2019-03-07 326.00 326.00 / pré>
Voici une version légèrement modifiée de la requête utilisant l'option ALL ROWS PER MATCH :
SELECT MR.symbol, MR.tradedate, MR.price, MR.matchnum, MR.classy, MR.startdate, MR.startprice, MR.bottomdate, MR.bottomprice, MR.enddate, MR.endprice, MR. maxpriceFROM dbo.Ticker MATCH_RECOGNIZE (PARTITION BY symbole ORDER BY tradedate MEASURES MATCH_NUMBER() AS matchnum, CLASSIFIER() AS classy, A.tradedate AS startdate, A.price AS startprice, LAST(B.tradedate) AS bottomdate, LAST(B. prix) AS bottomprice, LAST(C.tradedate) AS enddate, LAST(C.price) AS endprice, MAX(U.price) AS maxprice TOUTES LES LIGNES PAR MATCH APRÈS LE MATCH SAUTER LA DERNIÈRE LIGNE MODÈLE (A B+ C+) SOUS-ENSEMBLE U =(A, B, C) DEFINE B AS B.price PREV(C.price) ) AS MR;
Voici le résultat attendu de cette requête :
symbol tradedate price matchnum classy startdate startprice bottomdate bottomprice enddate endprice maxprice------ ---------- ------ -------- ----- - ---------- ---------- ---------- ----------- -------- -- --------- --------STOCK1 2019-02-13 151,00 1 A 2019-02-13 151,00 NULL NULL NULL NULL 151,00STOCK1 2019-02-14 148,00 1 B 2019- 02-13 151,00 2019-02-14 148,00 NULL NULL 151,00STOCK1 2019-02-15 146,00 1 B 2019-02-13 151,00 2019-02-15 146,00 NULL NULL 151,00B020 1 2019-02-18 13 151,00 2019-02-18 142.00 NULL NULL 151.00STOCK1 2019-02-19 144.00 1 C 2019-02-13 151.00 2019-02-18 142.00 2019-02-19 144,00 151,00STOCK1 2019-02-20 152.00 1 C 2019- 02-13 151.00 2019-02-18 142.00 2019-02-20 152.00 152.00STOCK1 2019-02 -27 154,00 2 A 2019-02-27 154,00 NULL NULL NULL NULL 154,00STOCK1 2019-02-28 153,00 2 B 2019-02-27 154,00 2019-02-28 153,00 B NULL NULL 154,00STOCK1 2019-0193 -02-27 154,00 2019-03-01 145,00 NULL NULL 154,00STOCK1 2019-03-04 140,00 2 B 2019-02-27 154,00 2019-03-04 140,00 NULL NULL 154,00STOCK1 2019-03-04 140,00STOCK1 2019-03-04 140,00 -27 154,00 2019-03-04 140,00 2019-03-05 142.00 154.00STOCK1 2019-03-06 143,00 2 C 2019-02-27 154.00 2019-03-04 140,00 2019-03-06 143,00 154.00STOCK2 2019-02-14 329.00 1 A 2019-02-14 329.00 NULL NULL NULL NULL 329.00STOCK2 2019-02-15 326.00 1 B 2019-02-14 329.00 2019-02-15 326.00 NULL NULL 329.00STOCK2 2019-02-15 2019-02-14 329.00 2019-02-18 325.00 NULL NULL 329.00STOCK2 2019-02-19 326.00 1 C 2019-02-14 329.00 2019-02-18 325.00 2019-02-19 326.00 329.00Stock2 2019-02-20 328.00 1 C 2019-02-14 329.00 2019-02-18 325.00 2019-02-20 328.00 329.00STOCK2 2019-02-21 326.00 2 A 2019-02-21 326.00 NULL NULL NULL NULL 326.00STOCK2 20 2019-02-21 326,00 2019-02-22 320,00 NULL NULL 326,00STOCK2 2019-02-25 317,00 2 B 2019-02-21 326,00 2019-02-25 317,00 NULL NULL 326,00STOCK2 2019 02-21 326.00 2019-02-25 317.00 2019-02-26 319.00 326.00STOCK2 2019-02-27 325.00 2 C 2019-02-21 326.00 2019-02-25 317.00 2019-02-27 325.00 326.00STOCK2 2019-03- 01 324,00 3 A 2019-03-01 324,0 0 NULL NULL NULL NULL 324.00STOCK2 2019-03-04 321.00 3 B 2019-03-01 324.00 2019-03-04 321.00 NULL NULL 324.00STOCK2 2019-03-05 319.00 3 B 2019-03-01 321.00 3 B 2019-03-01 321 319.00 NULL NULL 324.00STOCK2 2019-03-06 322.00 3 C 2019-03-01 324.00 2019-03-05 319.00 2019-03-06 322.00 324.00STOCK2 2019-03-07 326.00 3 C 2019-03-01 324.00 2019-03 -05 319.00 2019-03-07 326.00 326.0027 ligne(s) affectée(s).
Remarquez l'ajout de la mesure classy basée sur la fonction CLASSIFIER. Cette fonction renvoie une chaîne représentant la variable de modèle de ligne à laquelle la ligne de résultat est associée (dans notre cas, A, B ou C).
Fonctionnalité R020, "Reconnaissance du modèle de ligne :clause WINDOW"
La fonctionnalité R020 utilise la reconnaissance de modèle de ligne dans le cadre de la clause de fenêtrage OVER (ou de la clause WINDOW lors de la dénomination d'une spécification de fenêtre) pour restreindre davantage un cadre de fenêtre. Tout comme la partition de fenêtre restreint les lignes de l'expression de la table d'entrée (FROM… WHERE… GROUP BY… HAVING), et le cadre de fenêtre restreint davantage la partition de fenêtre, avec la fonction R020, vous restreignez davantage le cadre de fenêtre complet à un cadre de fenêtre réduit fait de la sous-séquence de lignes constituant la correspondance de modèle. Voici une requête illustrant cette fonctionnalité avec la clause WINDOW, utilisant une spécification de correspondance de modèle de ligne similaire à celle utilisée dans la première requête de cet article :
SELECT T.symbol, T.tradedate, T.price, startdate OVER W, startprice OVER W, bottomdate OVER W, bottomprice OVER W, enddate OVER W, endprice OVER W, maxprice OVER WFROM dbo.Ticker TWINDOW W AS ( PARTITION BY symbole ORDER BY tradedate MESURES A.tradedate AS startdate, A.price AS startprice, LAST(B.tradedate) AS bottomdate, LAST(B.price) AS bottomprice, LAST(C.tradedate) AS enddate, LAST(C. price) AS endprice, MAX(U.price) AS maxprice ROWS BETWEEN CURRENT ROW AND UNBOUNDED FOLLOWING AFTER MATCH SKIP PAST LAST ROW INITIAL -- le modèle doit commencer à la première ligne du cadre de fenêtre complet ; l'alternative est SEEK PATTERN (A B+ C+) SUBSET U =(A, B, C) DEFINE B AS B.price PREV(C.price) );
Lors de l'utilisation de la reconnaissance de modèle de ligne avec fenêtrage, le cadre de fenêtre complet doit commencer à la ligne actuelle. Notez l'utilisation de l'option INITIAL dans cette requête. Cette option signifie que vous obtenez une correspondance uniquement si le modèle commence par la ligne actuelle. L'alternative est SEEK, ce qui signifie qu'une recherche de correspondance commence par la ligne actuelle, mais est autorisée jusqu'à la fin du cadre de fenêtre complet. Dans tous les cas, si une correspondance est trouvée, le cadre de fenêtre réduit se compose uniquement des lignes de correspondance de modèle, sinon, le cadre de fenêtre réduit est vide. Une seule correspondance de modèle de ligne par cadre de fenêtre complet est recherchée.
Observez dans la liste SELECT de la requête que vous pouvez renvoyer des mesures définies dans la clause MEASURES, calculées sur W, qui est le cadre de fenêtre réduit.
Rappelez le résultat de la première requête de cet article, en utilisant la reconnaissance du modèle de ligne dans la clause FROM, avec l'option ONE ROW PER MATCH :
symbol matchnum startdate startprice bottomdat bottomprice enddate endprice maxprice------ -------- ---------- ---------- ---- ------ ----------- ---------- -------- --------STOCK1 1 2019-02-13 151,00 2019-02-18 142.00 2019-02-20 152.00 152.00stock1 2 2019-02-27 154,00 2019-03-04 140,00 2019-03-06 143,00 154.00stock2 1 2019-02-14 329.00 2019-02-18 325.00 2019 -02-20 328.00 329.00STOCK2 2 2019-02-21 326.00 2019-02-25 317.00 2019-02-27 325.00 326.00STOCK2 3 2019-03-01 324.00 2019-03-05 319.00 2019-03-07 326.00 326.00 / pré>
Voici le résultat attendu de notre dernière requête, utilisant la reconnaissance de modèle de ligne dans la clause WINDOW :
symbole tradedate prix startdate startprice bottomdate bottomprice endprice endprice maxprice------ ---------- ------ ---------- ----- ----- ---------- ----------- ---------- -------- ------ --STOCK1 12/02/2019 150,00 NULL NULL NULL NULL NULL NULL NULLSTOCK1 13/02/2019 151,00 13/02/2019 151,00 18/02/2019 142,00 20/02/2019 152,00 152,00STOCK1 2480-10 NULL 2019 NULL NULL NULL NULL NULLSTOCK1 15/02/2019 146,00 NULL NULL NULL NULL NULL NULL NULLSTOCK1 18/02/2019 142,00 NULL NULL NULL NULL NULL NULL NULLSTOCK1 19/02/2019 144,00 NULL NULL NULL NULL NULL NULL NULLSTOCK1 2019-02-2019 NULL NULL NULL NULL NULL NULL NULLSTOCK1 2019-02-21 152,00 NULL NULL NULL NULL N 2019-02-25 154.00 NULL NULL NULL NULL NULL NULL NULLSTOCK1 2019-02-26 154.00 NULL NULL NULL NULL NULL NULL NULLSTOCK1 2019-02-90 154.00 02-27 154.00 2019-03-04 140.00 2019-03-06 143.00 154.00STOCK1 2019-02-28 153.00 NULL NULL NULL NULL NULL NULL NULLSTOCK1 2019-03-01 145.00 NULL NULL NULL NULL4 130.00 NULL100 NULL NULL NULL NULL NULL NULL NULLSTOCK1 2019-03-05 142,00 NULL NULL NULL NULL NULL NULL NULLSTOCK1 2019-03-06 143,00 NULL NULL NULL NULL NULL NULL NULLSTOCK1 2019-03-07 142,00 NULL NULL NULL N ULL NULL NULL NULLSTOCK1 2019-03-08 140,00 NULL NULL NULL NULL NULL NULL NULLSTOCK1 2019-03-11 138,00 NULL NULL NULL NULL NULL NULL NULLSTOCK2 2019-02-12 330,00 NULL NULL NULL NULL NULL NULL NULLSTOCK2 2019-02-13 NULL NULL NULL NULL NULL NULL NULLSTOCK2 2019-02-14 329,00 2019-02-14 329,00 2019-02-18 325,00 2019-02-20 328,00 329,00STOCK2 2019-02-15 326,00 NULL NULL NULL NULLSTOCK2 NULL00 325,00 NULL NULL NULL NULL NULL NULL NULLSTOCK2 2019-02-19 326,00 NULL NULL NULL NULL NULL NULL NULLSTOCK2 2019-02-20 328,00 NULL NULL NULL NULL NULL NULL NULLSTOCK2 2019-02-21 326,00 2019-02-21 326 019-02-25 317,00 2019-02-27 325,00 326,00STOCK2 2019-02-22 320,00 NULL NULL NULL NULL NULL NULL NULLSTOCK2 2019-02-25 317,00 NULL NULL NULL NULL NULL NULL NULLSTOCK2 2019-02-20 NULL NULL NULL NULL NULLSTOCK2 2019-02-27 325.00 NULL NULL NULL NULL NULL NULL NULLSTOCK2 2019-02-28 322.00 NULL NULL NULL NULL NULL NULL NULLSTOCK2 2019-03-01 324.00 2019-03-01 324.00 2019-03-05 324.00 2019-03-05 319.00 -07 326,00 326,00STOCK2 2019-03-04 321,00 NULL NULL NULL NULL NULL NULL NULLSTOCK2 2019-03-05 319,00 NULL NULL NULL NULL NULL NULL NULLSTOCK2 2019-03-06 322,00 NULL NULL NULL NULL NULL NULL NULLSTOCK2 20-07-07-30 20-07-30 NUL NULL NULL NULL NULL NULL NULLSTOCK2 2019-03-08 326.00 NULL NULL NULL NULL NULL NULL NULLSTOCK2 2019-03-11 324.00 NULL NULL NULL NULL NULL NULL NULL40 ligne(s) affectée(s).
Observez que vous obtenez toutes les lignes détaillées dans la sortie, et lorsqu'une correspondance de modèle commence, vous obtenez le résultat des mesures de modèle de ligne demandées par rapport au cadre de fenêtre réduit.
Votez
Il est tout à fait entendu que pour Microsoft, ajouter une fonctionnalité à T-SQL, en particulier une fonctionnalité aussi importante, est un investissement assez important. Mais ce qui est génial avec les fonctionnalités ajoutées à T-SQL, c'est qu'elles y restent à peu près pour toujours. Il y a une énorme communauté avide d'améliorations T-SQL comme celle-ci.
Si vous pensez que la reconnaissance des modèles de ligne est un ajout important à SQL Server, assurez-vous de voter. En outre, Microsoft est plus susceptible de donner la priorité à une fonctionnalité proposée s'il connaît des clients et des cas d'utilisation qui pourraient en bénéficier, et qu'à l'heure actuelle, ces clients utilisent d'autres produits ou des solutions plus complexes. Si vous ou vos clients considérez le RPR comme un avantage pour vous et avez des cas d'utilisation que vous pouvez partager, assurez-vous d'ajouter des commentaires à l'élément de commentaires et d'en informer Microsoft.