{"id":9898,"date":"2026-10-14T18:02:35","date_gmt":"2026-10-14T18:02:35","guid":{"rendered":"http:\/\/french.arabpsychology.com\/statistics\/comment-utiliser-fonction-substr-sas-exemples\/"},"modified":"2026-10-14T18:02:35","modified_gmt":"2026-10-14T18:02:35","slug":"comment-utiliser-fonction-substr-sas-exemples","status":"publish","type":"psych_stat","link":"https:\/\/french.arabpsychology.com\/?psych_stat=comment-utiliser-fonction-substr-sas-exemples","title":{"rendered":"Comment utiliser la fonction SUBSTR dans SAS (avec exemples)"},"content":{"rendered":"<p>Dans le domaine de l&rsquo;analyse statistique avanc\u00e9e et de la science des donn\u00e9es biom\u00e9dicales, \u00e9pid\u00e9miologiques et psychosociales, le syst\u00e8me d&rsquo;analyse statistique <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https:\/\/www.sas.com\">SAS (Statistical Analysis System)<\/a> demeure une r\u00e9f\u00e9rence incontournable. Les chercheurs et analystes sont quotidiennement confront\u00e9s \u00e0 des volumes massifs d&rsquo;informations h\u00e9t\u00e9rog\u00e8nes au sein desquelles les variables alphanum\u00e9riques jouent un r\u00f4le pivot. Loin de se limiter \u00e0 de simples libell\u00e9s descriptifs, les cha\u00eenes de caract\u00e8res renferment fr\u00e9quemment des structures informationnelles composites : identifiants de protocoles multicentriques, codifications hi\u00e9rarchiques de la classification internationale des maladies, horodatages d&rsquo;exp\u00e9rimentations comportementales ou s\u00e9quences s\u00e9rialis\u00e9es de r\u00e9ponses psychom\u00e9triques. L&rsquo;extraction pr\u00e9cise, robuste et reproductible de sous-composants textuels constitue donc le socle indispensable sur lequel repose l&rsquo;ensemble de la cha\u00eene de traitement et de mod\u00e9lisation statistique.<\/p>\n<p>Au c\u0153ur de cette m\u00e9canique de transformation des donn\u00e9es, la fonction <strong>SUBSTR<\/strong> (pour <em>sub-string<\/em> ou sous-cha\u00eene) s&rsquo;impose comme un outil fondamental et polyvalent. Int\u00e9gr\u00e9e nativement au moteur d&rsquo;ex\u00e9cution de l&rsquo;\u00e9tape DATA, elle permet d&rsquo;isoler avec une exactitude math\u00e9matique une s\u00e9quence de caract\u00e8res d\u00e9termin\u00e9e au sein d&rsquo;une cha\u00eene h\u00f4te, ou inversement de substituer un segment textuel par un autre lorsqu&rsquo;elle est mobilis\u00e9e en tant que pseudo-variable. La ma\u00eetrise exhaustive de sa syntaxe, de ses m\u00e9canismes d&rsquo;\u00e9valuation interne lors de la compilation et de l&rsquo;ex\u00e9cution, ainsi que de ses interactions avec le <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https:\/\/documentation.sas.com\">Vecteur de Donn\u00e9es du Programme (PDV, Program Data Vector)<\/a>, conditionne directement la validit\u00e9 scientifique des jeux de donn\u00e9es r\u00e9sultants. Une m\u00e9connaissance de ses subtilit\u00e9s op\u00e9ratoires expose l&rsquo;analyste \u00e0 des erreurs de troncature silencieuse, \u00e0 des d\u00e9calages d&rsquo;indices positionnels ou \u00e0 des avertissements critiques dans le journal d&rsquo;ex\u00e9cution.<\/p>\n<p>Ce guide exhaustif a pour vocation d&rsquo;analyser en profondeur les principes th\u00e9oriques, les modalit\u00e9s d&rsquo;impl\u00e9mentation pratique et les ramifications m\u00e9thodologiques de la fonction <strong>SUBSTR<\/strong> dans l&rsquo;environnement SAS. \u00c0 travers une progression didactique rigoureuse, nous examinerons les fondements de l&rsquo;indexation textuelle, d\u00e9taillerons les quatre grandes m\u00e9thodes d&rsquo;extraction par coordonn\u00e9es statiques ou dynamiques, explorerons l&rsquo;usage bidirectionnel de la fonction pour la modification en m\u00e9moire, et \u00e9tablirons des comparaisons directes avec les fonctions connexes du syst\u00e8me. Destin\u00e9e aux biostatisticiens, m\u00e9thodologistes et ing\u00e9nieurs de donn\u00e9es soucieux de rigueur algorithmique, cette monographie fournit les cl\u00e9s conceptuelles et op\u00e9rationnelles n\u00e9cessaires pour s\u00e9curiser vos cha\u00eenes de traitement textuel au standard de la recherche empirique la plus exigeante.<\/p>\n<h2>1. Introduction \u00e0 la fonction SUBSTR dans SAS et son importance m\u00e9thodologique<\/h2>\n<h3>1.1 Fondements de la manipulation de cha\u00eenes de caract\u00e8res dans SAS<\/h3>\n<p>Dans le paradigme computationnel de SAS, les donn\u00e9es sont formellement divis\u00e9es en deux grands types primitifs : les variables num\u00e9riques et les variables caract\u00e8res. Si les premi\u00e8res font traditionnellement l&rsquo;objet de calculs math\u00e9matiques et d&rsquo;estimations param\u00e9triques, les secondes repr\u00e9sentent souvent l&rsquo;ossature organisationnelle des bases de donn\u00e9es de recherche. Le nettoyage, l&rsquo;harmonisation et la structuration des variables textuelles repr\u00e9sentent fr\u00e9quemment plus de la moiti\u00e9 du temps allou\u00e9 \u00e0 la pr\u00e9paration des donn\u00e9es (le <em>data wrangling<\/em>). Dans les protocoles cliniques ou les vastes enqu\u00eates sociod\u00e9mographiques, les donn\u00e9es textuelles brutes pr\u00e9sentent rarement une forme directement exploitable par les proc\u00e9dures de mod\u00e9lisation telles que PROC GLM, PROC LOGISTIC ou PROC MIXED.<\/p>\n<p>Les variables textuelles dans SAS se caract\u00e9risent par une allocation de m\u00e9moire \u00e0 longueur fixe, d\u00e9termin\u00e9e d\u00e8s la phase de compilation de l&rsquo;\u00e9tape DATA. Contrairement \u00e0 d&rsquo;autres langages de programmation contemporains qui adoptent des cha\u00eenes dynamiques termin\u00e9es par un caract\u00e8re nul ou g\u00e9r\u00e9es par des pointeurs \u00e9lastiques, SAS alloue un nombre fixe d&rsquo;octets \u00e0 chaque variable caract\u00e8re. Toute position non occup\u00e9e par un glyphe visible est alors automatiquement combl\u00e9e par des espaces de remplissage (d\u00e9sign\u00e9s sous le terme de <em>trailing blanks<\/em>). Cette particularit\u00e9 architecturale impose une vigilance m\u00e9thodologique constante lors de l&rsquo;application des fonctions de manipulation textuelle, car la longueur apparente d&rsquo;une valeur ne correspond pas n\u00e9cessairement \u00e0 sa longueur physique en m\u00e9moire.<\/p>\n<p>Le catalogue de fonctions de caract\u00e8res mis \u00e0 disposition par le moteur SAS comprend des dizaines d&rsquo;op\u00e9rateurs sp\u00e9cialis\u00e9s : concat\u00e9nation, recherche de motifs, suppression d&rsquo;espaces et d\u00e9coupage positionnel. Au sein de cet arsenal, la fonction <strong>SUBSTR<\/strong> occupe une place cardinale. Elle constitue l&rsquo;op\u00e9rateur \u00e9l\u00e9mentaire d&rsquo;acc\u00e8s direct par indexation positionnelle. Alors que des fonctions comme SCAN reposent sur la d\u00e9tection de d\u00e9limiteurs variables, <strong>SUBSTR<\/strong> op\u00e8re par g\u00e9om\u00e9trie fixe ou calcul\u00e9e. Elle offre ainsi une vitesse de traitement optimale et un d\u00e9terminisme absolu, deux qualit\u00e9s indispensables lorsqu&rsquo;il s&rsquo;agit de garantir la tra\u00e7abilit\u00e9 int\u00e9grale des transformations au sein de pipelines analytiques certifi\u00e9s.<\/p>\n<h3>1.2 Contexte d&rsquo;application dans le traitement des donn\u00e9es de recherche<\/h3>\n<p>L&rsquo;utilit\u00e9 empirique de la fonction <strong>SUBSTR<\/strong> se r\u00e9v\u00e8le pleinement lors de la manipulation d&rsquo;identifiants de recherche complexes. Dans le cadre d&rsquo;essais cliniques multicentriques standardis\u00e9s par les normes du <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https:\/\/www.cdisc.org\">Consortium CDISC (Clinical Data Interchange Standards Consortium)<\/a>, l&rsquo;identifiant unique d&rsquo;un participant (souvent nomm\u00e9 <code>USUBJID<\/code>) r\u00e9sulte fr\u00e9quemment de la concat\u00e9nation de codes signifiants : le code du pays d&rsquo;inclusion, l&rsquo;identifiant du centre hospitalier, le num\u00e9ro de la cohorte d&rsquo;attribution et le rang chronologique du patient au sein du centre. Par exemple, une cha\u00eene telle que \u00ab\u00a0FRA-014-COH2-0089\u00a0\u00bb condense quatre niveaux hi\u00e9rarchiques distincts. L&rsquo;analyste doit \u00eatre capable d&rsquo;isoler avec une certitude absolue le segment repr\u00e9sentant le centre (\u00ab\u00a0014\u00a0\u00bb) ou la cohorte (\u00ab\u00a0COH2\u00a0\u00bb) pour contr\u00f4ler d&rsquo;\u00e9ventuels effets de grappe ou stratifier ses mod\u00e8les de survie.<\/p>\n<p>Un autre domaine d&rsquo;\u00e9lection concerne le d\u00e9pouillement d&rsquo;instruments psychom\u00e9triques et de questionnaires standardis\u00e9s. De nombreux syst\u00e8mes de saisie informatis\u00e9e ou dispositifs de passation de tests cognitifs exportent les r\u00e9ponses sous la forme d&rsquo;un vecteur compact de caract\u00e8res continus. Une s\u00e9quence de vingt chiffres cons\u00e9cutifs sans s\u00e9parateur peut ainsi enregistrer l&rsquo;int\u00e9gralit\u00e9 des r\u00e9ponses d&rsquo;un sujet \u00e0 une \u00e9chelle de d\u00e9pression ou d&rsquo;anxi\u00e9t\u00e9 de type Likert. La fonction <strong>SUBSTR<\/strong> permet d&rsquo;it\u00e9rer \u00e0 travers cette cha\u00eene compact\u00e9e afin de ventiler chaque r\u00e9ponse dans une variable distincte, autorisant ensuite le calcul des scores composites, l&rsquo;analyse factorielle confirmatoire ou l&rsquo;\u00e9valuation de la coh\u00e9rence interne par le coefficient alpha de Cronbach.<\/p>\n<p>Enfin, la standardisation des m\u00e9tadonn\u00e9es issues d&rsquo;instruments d&rsquo;exp\u00e9rimentation comportementale (comme les syst\u00e8mes d&rsquo;oculom\u00e9trie ou les dispositifs d&rsquo;imagerie fonctionnelle) requiert souvent la dissection fine d&rsquo;horodatages ou de codes d&rsquo;\u00e9tat crypt\u00e9s. L&rsquo;int\u00e9grit\u00e9 r\u00e9f\u00e9rentielle des bases de donn\u00e9es longitudinales d\u00e9pend de la capacit\u00e9 du statisticien \u00e0 extraire fid\u00e8lement les pr\u00e9fixes de dates ou les suffixes de version de protocole sans introduire de biais d&rsquo;alignement. Dans tous ces cas d&rsquo;usage, <strong>SUBSTR<\/strong> se pr\u00e9sente comme le garant de la granularit\u00e9 de l&rsquo;information brute, permettant de transformer une masse textuelle monolithique en indicateurs cat\u00e9goriels ou ordinaux exploitables.<\/p>\n<h3>1.3 Objectifs p\u00e9dagogiques et structure de l&rsquo;analyse<\/h3>\n<p>L&rsquo;objectif de cette \u00e9tude technique est de d\u00e9mystifier le fonctionnement intrins\u00e8que de la fonction <strong>SUBSTR<\/strong> et de fournir un cadre m\u00e9thodologique exhaustif pour son impl\u00e9mentation dans les environnements de production et de recherche SAS. Bien que sa syntaxe de base paraisse d&rsquo;une apparente simplicit\u00e9, l&rsquo;interaction entre ses arguments, les longueurs de variables et les sp\u00e9cificit\u00e9s de compilation r\u00e9serve de nombreux pi\u00e8ges aux praticiens non avertis. L&rsquo;indexation bas\u00e9e sur 1 (et non sur 0 comme dans les langages d\u00e9riv\u00e9s du C ou en Python), la gestion des d\u00e9passements de limites et la modification en place constituent des dimensions techniques cruciales qui n\u00e9cessitent une clarification approfondie.<\/p>\n<p>Pour r\u00e9pondre \u00e0 ces enjeux, notre analyse s&rsquo;articule autour d&rsquo;une progression syst\u00e9matique. Apr\u00e8s avoir pos\u00e9 l&rsquo;anatomie fonctionnelle et le comportement du compilateur vis-\u00e0-vis des types et longueurs de variables, nous pr\u00e9senterons de mani\u00e8re d\u00e9taill\u00e9e les quatre grandes m\u00e9thodes d&rsquo;extraction textuelle : l&rsquo;isolation de pr\u00e9fixes fixes, l&rsquo;extraction de plages interm\u00e9diaires, le calcul dynamique d&rsquo;indices pour extraire des suffixes, et l&rsquo;int\u00e9gration logique dans des structures conditionnelles de segmentation. Chaque m\u00e9thode sera \u00e9tay\u00e9e par des instructions ex\u00e9cutables et contextualis\u00e9e dans des sc\u00e9narios r\u00e9alistes d&rsquo;analyse de donn\u00e9es empiriques.<\/p>\n<p>La seconde moiti\u00e9 de ce document approfondira l&rsquo;utilisation m\u00e9connue mais puissante de <strong>SUBSTR<\/strong> en tant que pseudo-variable d&rsquo;affectation pour modifier directement le contenu de la m\u00e9moire tampon, avant de proc\u00e9der \u00e0 une analyse comparative avec les fonctions concurrentes (SCAN, INDEX, TRANWRD, expressions r\u00e9guli\u00e8res PRX). Nous aborderons ensuite la gestion des encodages multioctets et des jeux de caract\u00e8res internationaux, proposerons trois cas d&rsquo;application concrets issus de la recherche translationnelle, et fournirons une grille diagnostique compl\u00e8te des anomalies r\u00e9pertori\u00e9es dans le journal d&rsquo;ex\u00e9cution (le fameux <em>SAS Log<\/em>), compl\u00e9t\u00e9e par des recommandations d&rsquo;optimisation pour les bases de donn\u00e9es volumineuses.<\/p>\n<h2>2. Anatomie et syntaxe fondamentale de la fonction SUBSTR<\/h2>\n<h3>2.1 D\u00e9composition des arguments de la fonction SUBSTR(source, position, n)<\/h3>\n<p>L&rsquo;utilisation de la fonction <strong>SUBSTR<\/strong> dans une \u00e9tape DATA repose sur une signature formelle standardis\u00e9e qui mobilise de deux \u00e0 trois arguments selon la nature de l&rsquo;op\u00e9ration envisag\u00e9e :<\/p>\n<p><code>SUBSTR(source, position, &lt;n&gt;)<\/code><\/p>\n<p>Le premier argument, d\u00e9sign\u00e9 par <strong>source<\/strong>, sp\u00e9cifie la cha\u00eene de caract\u00e8res \u00e0 partir de laquelle l&rsquo;extraction doit \u00eatre op\u00e9r\u00e9e. Cet argument peut \u00eatre constitu\u00e9 par le nom d&rsquo;une variable caract\u00e8re pr\u00e9existante dans la table d&rsquo;entr\u00e9e, une constante textuelle encadr\u00e9e par des guillemets simples ou doubles, ou encore le r\u00e9sultat renvoy\u00e9 par une autre expression ou fonction retournant une cha\u00eene (par exemple, le r\u00e9sultat d&rsquo;un appel imbriqu\u00e9 \u00e0 TRIM ou CATX). Si la variable source contient une valeur num\u00e9rique, le processeur de compilation de SAS \u00e9mettra une note de conversion implicite de type num\u00e9rique vers caract\u00e8re, ce qui, bien que g\u00e9r\u00e9 automatiquement, constitue une d\u00e9viation des bonnes pratiques de programmation d\u00e9fensive.<\/p>\n<p>Le second argument, <strong>position<\/strong>, indique l&rsquo;indice du caract\u00e8re marquant le d\u00e9but de la sous-cha\u00eene \u00e0 extraire. Il est imp\u00e9ratif de souligner que SAS utilise un syst\u00e8me d&rsquo;indexation ordinal bas\u00e9 sur 1 (<em>1-based indexing<\/em>). Par cons\u00e9quent, le premier caract\u00e8re d&rsquo;une cha\u00eene se situe syst\u00e9matiquement \u00e0 la position 1, le second \u00e0 la position 2, et ainsi de suite. Cet argument doit s&rsquo;\u00e9valuer \u00e0 un nombre entier strictement positif. Si la valeur de position est un nombre d\u00e9cimal, SAS tronque automatiquement la partie fractionnaire pour ne retenir que la partie enti\u00e8re. En revanche, si la position est \u00e9valu\u00e9e \u00e0 une valeur inf\u00e9rieure ou \u00e9gale \u00e0 z\u00e9ro, ou si elle d\u00e9passe strictement la longueur physique de la cha\u00eene source, le moteur SAS g\u00e9n\u00e8re un avertissement d&rsquo;argument invalide dans le journal d&rsquo;ex\u00e9cution.<\/p>\n<p>Le troisi\u00e8me argument, <strong>n<\/strong>, est un param\u00e8tre optionnel qui quantifie exactement le nombre de caract\u00e8res que l&rsquo;algorithme doit collecter \u00e0 partir de l&rsquo;indice de d\u00e9part. Lorsqu&rsquo;il est fourni, il doit s&rsquo;agir d&rsquo;un entier positif repr\u00e9sentant la largeur de la fen\u00eatre d&rsquo;extraction. L&rsquo;omission de ce troisi\u00e8me param\u00e8tre produit un comportement par d\u00e9faut parfaitement document\u00e9 mais souvent source d&rsquo;ambigu\u00eft\u00e9 : la fonction extrait l&rsquo;int\u00e9gralit\u00e9 des caract\u00e8res restants, depuis la position d&rsquo;ancrage sp\u00e9cifi\u00e9e jusqu&rsquo;\u00e0 l&rsquo;extr\u00e9mit\u00e9 physique finale de la cha\u00eene source. Cette caract\u00e9ristique s&rsquo;av\u00e8re particuli\u00e8rement utile lorsque l&rsquo;on souhaite capter le r\u00e9sidu textuel d&rsquo;une variable sans devoir mesurer pr\u00e9alablement sa terminaison.<\/p>\n<h3>2.2 Attribution de longueur et typage de la variable r\u00e9sultante<\/h3>\n<p>L&rsquo;un des aspects les plus techniques et critiques de l&rsquo;utilisation de <strong>SUBSTR<\/strong> r\u00e9side dans la d\u00e9termination par le compilateur de la longueur de la nouvelle variable g\u00e9n\u00e9r\u00e9e lors d&rsquo;une assignation. Lors de la phase de compilation du Data Step, avant m\u00eame qu&rsquo;une seule ligne d&rsquo;observation ne soit lue en m\u00e9moire, SAS examine la premi\u00e8re instruction o\u00f9 appara\u00eet la nouvelle variable cible afin de dimensionner son espace m\u00e9moire dans le Vecteur de Donn\u00e9es du Programme. Si la variable r\u00e9ceptrice n&rsquo;a pas fait l&rsquo;objet d&rsquo;une instruction explicite <code>LENGTH<\/code> en amont, SAS applique une r\u00e8gle de d\u00e9rivation par d\u00e9faut.<\/p>\n<p>Par d\u00e9faut, lorsque l&rsquo;on \u00e9crit <code>nouvelle_var = SUBSTR(source_var, pos, n);<\/code>, la longueur attribu\u00e9e \u00e0 <code>nouvelle_var<\/code> d\u00e9pend directement des sp\u00e9cifications fournies :<\/p>\n<ul>\n<li>Si le param\u00e8tre <code>n<\/code> est sp\u00e9cifi\u00e9 sous forme de constante num\u00e9rique litt\u00e9rale (par exemple, 4), la nouvelle variable se verra attribuer une longueur de 4 octets.<\/li>\n<li>Si le param\u00e8tre <code>n<\/code> est omis, la nouvelle variable h\u00e9ritera d&rsquo;une longueur \u00e9quivalente \u00e0 la longueur totale d\u00e9clar\u00e9e de la variable <code>source_var<\/code>.<\/li>\n<li>Si le param\u00e8tre <code>n<\/code> est le r\u00e9sultat d&rsquo;une expression variable ou dynamique (par exemple, calcul\u00e9 par une formule), SAS attribue conventionnellement \u00e0 la variable cible la longueur totale de la variable source, afin de pr\u00e9venir tout risque de d\u00e9bordement m\u00e9moire potentiel lors de l&rsquo;ex\u00e9cution.<\/li>\n<\/ul>\n<p>Cette heuristique de compilation peut engendrer des effets pervers si le flux du programme r\u00e9assigne ult\u00e9rieurement \u00e0 cette m\u00eame variable des cha\u00eenes de longueurs sup\u00e9rieures, provoquant alors une troncature silencieuse d\u00e9sastreuse sans la moindre \u00e9mission d&rsquo;erreur. Pour pr\u00e9munir le pipeline analytique contre toute alt\u00e9ration d&rsquo;int\u00e9grit\u00e9, la r\u00e8gle m\u00e9thodologique fondamentale consiste \u00e0 d\u00e9clarer imp\u00e9rativement la longueur de toute variable textuelle d\u00e9riv\u00e9e via une instruction <code>LENGTH<\/code> plac\u00e9e au tout d\u00e9but du bloc DATA. Cette d\u00e9claration pr\u00e9alable neutralise les automatismes du compilateur et garantit que l&rsquo;espace allou\u00e9 en octets correspond exactement aux exigences de dimensionnement du projet.<\/p>\n<h3>2.3 Consid\u00e9rations relatives aux espaces et au rembourrage (padding)<\/h3>\n<p>La distinction entre la longueur physique de stockage d&rsquo;une variable et sa longueur s\u00e9mantique repr\u00e9sente une pierre d&rsquo;achoppement fr\u00e9quente dans la programmation SAS. Lorsqu&rsquo;une variable caract\u00e8re est d\u00e9finie avec une longueur de 20 octets (via <code>LENGTH code $20;<\/code>) et que l&rsquo;on y enregistre une valeur textuelle courte telle que \u00ab\u00a0INSERM\u00a0\u00bb, SAS comble les 14 octets restants avec des caract\u00e8res d&rsquo;espace (code ASCII 32). Ces espaces de fin, qualifi\u00e9s de <em>trailing blanks<\/em>, font partie int\u00e9grante de la valeur stock\u00e9e dans le PDV et participent \u00e0 toute \u00e9valuation positionnelle qui n&rsquo;en tiendrait pas compte.<\/p>\n<p>Si l&rsquo;on utilise la fonction <strong>SUBSTR<\/strong> sans pr\u00e9caution sur une telle variable, en omettant par exemple le troisi\u00e8me argument <code>n<\/code> pour r\u00e9cup\u00e9rer la fin de la cha\u00eene, la sous-cha\u00eene r\u00e9sultante contiendra in\u00e9vitablement l&rsquo;ensemble de ces espaces de rembourrage. Ce ph\u00e9nom\u00e8ne pose des difficult\u00e9s consid\u00e9rables lors de concat\u00e9nations ult\u00e9rieures ou lors de comparaisons d&rsquo;\u00e9galit\u00e9 logique. Une cha\u00eene extraite contenant des espaces r\u00e9siduels ne correspondra pas \u00e0 une constante litt\u00e9rale compacte, faussant ainsi les instructions conditionnelles ult\u00e9rieures.<\/p>\n<p>Il est donc essentiel de conjuguer l&rsquo;usage de <strong>SUBSTR<\/strong> avec des fonctions de nettoyage pr\u00e9liminaire telles que <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https:\/\/documentation.sas.com\/?docsetId=lefunctionsref&#038;docsetTarget=p0591gqoxb21l0n1t4161l2r6j41.htm&#038;docsetVersion=9.4\">STRIP<\/a> ou <code>TRIM<\/code>. Tandis que <code>TRIM<\/code> retire les espaces situ\u00e9s exclusivement \u00e0 la droite de la cha\u00eene, <code>STRIP<\/code> supprime simultan\u00e9ment les espaces de d\u00e9but et de fin. De plus, la fonction <code>LENGTH<\/code> (qui renvoie l&rsquo;indice du dernier caract\u00e8re non blanc) et la fonction <code>LENGTHN<\/code> jouent un r\u00f4le d&rsquo;\u00e9talonnage indispensable lorsqu&rsquo;il s&rsquo;agit de calibrer dynamiquement l&rsquo;argument de position ou de largeur de <strong>SUBSTR<\/strong> face \u00e0 des donn\u00e9es textuelles h\u00e9t\u00e9rog\u00e8nes.<\/p>\n<h2>3. M\u00e9thode 1 : Extraction des N premiers caract\u00e8res d&rsquo;une cha\u00eene<\/h2>\n<h3>3.1 Fondements de l&rsquo;extraction pr\u00e9fixe<\/h3>\n<p>L&rsquo;extraction des premiers caract\u00e8res d&rsquo;une variable textuelle \u2014 commun\u00e9ment d\u00e9sign\u00e9e sous le terme d&rsquo;extraction pr\u00e9fixe \u2014 repr\u00e9sente l&rsquo;application la plus fr\u00e9quente et la plus \u00e9l\u00e9mentaire de la fonction <strong>SUBSTR<\/strong>. Sur le plan algorithmique, cette op\u00e9ration se caract\u00e9rise par la fixation invariable de l&rsquo;indice de d\u00e9part \u00e0 la valeur 1. En ancrant le d\u00e9but de la fen\u00eatre de lecture sur le tout premier caract\u00e8re physique de la cha\u00eene, l&rsquo;analyste ne fait varier que l&rsquo;\u00e9tendue du troisi\u00e8me param\u00e8tre <code>N<\/code> pour capturer la portion d\u00e9sir\u00e9e.<\/p>\n<p>Cette approche est universellement employ\u00e9e dans les nomenclatures professionnelles o\u00f9 les caract\u00e8res de t\u00eate v\u00e9hiculent une information classificatoire g\u00e9n\u00e9rale, tandis que les caract\u00e8res suivants apportent des pr\u00e9cisions de sous-niveaux. Dans le domaine de la pharmacovigilance, par exemple, les deux premiers caract\u00e8res d&rsquo;un identifiant de lot de fabrication peuvent renvoyer \u00e0 l&rsquo;usine d&#8217;embouteillage ou au pays de production. De m\u00eame, dans les protocoles de recherche clinique multicentriques, l&rsquo;identifiant global du sujet commence quasi syst\u00e9matiquement par le trigramme du centre investigateur (par exemple, \u00ab\u00a0PAR\u00a0\u00bb pour Paris, \u00ab\u00a0LYO\u00a0\u00bb pour Lyon, \u00ab\u00a0MAR\u00a0\u00bb pour Marseille).<\/p>\n<p>L&rsquo;ancrage en position 1 simplifie consid\u00e9rablement le calcul mental et la relecture du code. N\u00e9anmoins, sa rigueur repose sur l&rsquo;hypoth\u00e8se fondamentale que la cha\u00eene commence imm\u00e9diatement par l&rsquo;information s\u00e9mantique utile, sans \u00eatre pollu\u00e9e par des espaces initiaux parasites induits par des erreurs de saisie manuelle ou des imports de fichiers CSV mal format\u00e9s. Dans ce contexte, la certitude de la position 1 exige une validation pr\u00e9alable de la propret\u00e9 de la variable d&rsquo;origine.<\/p>\n<figure class=\"wpt-preserved-image\"><img fetchpriority=\"high\" decoding=\"async\" src=\"http:\/\/french.arabpsychology.com\/wp-content\/uploads\/2026\/09\/substr1.jpg\" alt=\"\" \/><\/figure>\n<h3>3.2 Impl\u00e9mentation technique et analyse de code SAS<\/h3>\n<p>Examinons l&rsquo;impl\u00e9mentation formelle d&rsquo;une extraction pr\u00e9fixe au sein d&rsquo;une \u00e9tape DATA standardis\u00e9e. Consid\u00e9rons une cohorte de recherche biom\u00e9dicale o\u00f9 les sujets sont identifi\u00e9s par une cha\u00eene standardis\u00e9e de 10 caract\u00e8res, dont les trois premiers identifient de mani\u00e8re univoque le site hospitalier d&rsquo;\u00e9valuation :<\/p>\n<p>Le bloc d&rsquo;instructions SAS s&rsquo;articule comme suit :<\/p>\n<ul>\n<li>D\u00e9finition de la table d&rsquo;entr\u00e9e via des lignes de donn\u00e9es brutes saisies sous <code>DATALINES<\/code>.<\/li>\n<li>D\u00e9claration formelle de la longueur de la nouvelle variable pr\u00e9fixe par l&rsquo;instruction <code>LENGTH site_id $3;<\/code>.<\/li>\n<li>Affectation de l&rsquo;extraction positionnelle : <code>site_id = SUBSTR(code_sujet, 1, 3);<\/code>.<\/li>\n<li>Visualisation et contr\u00f4le du r\u00e9sultat par la proc\u00e9dure <code>PROC PRINT<\/code>.<\/li>\n<\/ul>\n<p>Sur le plan de l&rsquo;ex\u00e9cution, lors du passage de chaque enregistrement dans le Vecteur de Donn\u00e9es du Programme, SAS lit la variable <code>code_sujet<\/code>. Arriv\u00e9 \u00e0 la ligne de transformation, le pointeur de lecture se positionne sur le caract\u00e8re 1, collecte 3 unit\u00e9s s\u00e9quentielles d&rsquo;octets, puis alloue cette cha\u00eene \u00e0 la variable <code>site_id<\/code>. Le r\u00e9sultat produit est un vecteur pur de 3 caract\u00e8res ne comportant aucun espace r\u00e9siduel, parfaitement dimensionn\u00e9 pour des op\u00e9rations de jointure relationnelle (<code>MERGE<\/code> ou <code>JOIN<\/code> SQL) avec une table de r\u00e9f\u00e9rence des centres hospitaliers participants.<\/p>\n<h3>3.3 Variantes et gestion des cas particuliers de pr\u00e9fixes<\/h3>\n<p>Bien que conceptuellement directe, l&rsquo;extraction pr\u00e9fixe soul\u00e8ve des cas particuliers qu&rsquo;il convient de traiter pr\u00e9ventivement. Que se passe-t-il si la longueur de la cha\u00eene source est inf\u00e9rieure au nombre <code>N<\/code> de caract\u00e8res r\u00e9clam\u00e9s ? Si une variable contient accidentellement la cha\u00eene \u00ab\u00a0FR\u00a0\u00bb (2 caract\u00e8res) et que l&rsquo;on invoque <code>SUBSTR(chaine, 1, 3)<\/code>, SAS r\u00e9agit en \u00e9mettant une notification explicite dans le journal : <code>NOTE: Invalid argument to function SUBSTR<\/code>, et assigne une valeur manquante textuelle (repr\u00e9sent\u00e9e par un espace blanc) \u00e0 la variable r\u00e9ceptrice. Ce comportement strict interrompt la continuit\u00e9 du traitement analytique pour l&rsquo;observation concern\u00e9e.<\/p>\n<p>Un autre \u00e9cueil classique r\u00e9side dans la pr\u00e9sence insidieuse d&rsquo;espaces en t\u00eate de cha\u00eene (<em>leading blanks<\/em>). Si la donn\u00e9e brute contient \u00a0\u00bb PAR001&Prime; (avec un espace initial), l&rsquo;appel \u00e0 <code>SUBSTR(chaine, 1, 3)<\/code> retournera \u00a0\u00bb PA\u00a0\u00bb, tronquant l&rsquo;identifiant du centre de sa derni\u00e8re lettre. Pour parer \u00e0 cette anomalie sans alt\u00e9rer la logique de position, il est imp\u00e9ratif d&rsquo;imbriquer une fonction d&rsquo;\u00e9lagage gauche ou globale : <code>SUBSTR(LEFT(chaine), 1, 3)<\/code> ou <code>SUBSTR(STRIP(chaine), 1, 3)<\/code>. Cette pr\u00e9caution garantit que l&rsquo;extraction s&rsquo;op\u00e8re sur le premier caract\u00e8re textuel effectif.<\/p>\n<p>Sur le plan des performances informatiques pures, il est l\u00e9gitime de comparer <strong>SUBSTR<\/strong> \u00e0 d&rsquo;autres alternatives de SAS, telles que l&rsquo;op\u00e9rateur d&rsquo;assignation tronqu\u00e9e ou des fonctions modernes comme <code>KLEFT<\/code>. <strong>SUBSTR<\/strong> demeure l&rsquo;instruction compil\u00e9e la plus v\u00e9loce en langage machine au sein du moteur SAS, car elle ne requiert aucun balayage d&rsquo;analyseur lexical (<em>parser<\/em>) : l&rsquo;acc\u00e8s au pointeur m\u00e9moire est direct et instantan\u00e9.<\/p>\n<h2>4. M\u00e9thode 2 : Extraction de caract\u00e8res dans une plage de positions sp\u00e9cifique<\/h2>\n<h3>4.1 S\u00e9lection d&rsquo;une sous-cha\u00eene m\u00e9diane \u00e0 positions fixes<\/h3>\n<p>L&rsquo;extraction de segments textuels situ\u00e9s au c\u0153ur d&rsquo;une cha\u00eene \u2014 ni au tout d\u00e9but, ni \u00e0 la toute fin \u2014 constitue la deuxi\u00e8me grande modalit\u00e9 d&rsquo;utilisation de <strong>SUBSTR<\/strong>. Dans cette configuration, le second argument <code>position<\/code> prend une valeur strictement sup\u00e9rieure \u00e0 1, mat\u00e9rialisant un d\u00e9calage d\u00e9lib\u00e9r\u00e9 vers l&rsquo;int\u00e9rieur de la s\u00e9quence textuelle. L&rsquo;analyste doit d\u00e9terminer avec une rigueur g\u00e9om\u00e9trique deux param\u00e8tres cardinaux : l&rsquo;indice de d\u00e9part pr\u00e9cis et l&rsquo;amplitude <code>n<\/code> de la fen\u00eatre d&rsquo;observation.<\/p>\n<p>Cette m\u00e9thode est particuli\u00e8rement adapt\u00e9e aux structures de codage positionnel dites \u00ab\u00a0\u00e0 champs fixes\u00a0\u00bb. Avant la g\u00e9n\u00e9ralisation des formats d&rsquo;\u00e9change auto-descriptifs comme le JSON ou le XML, la majorit\u00e9 des registres nationaux de sant\u00e9, des fichiers de recensement d\u00e9mographique et des bases de facturation hospitali\u00e8re (\u00e0 l&rsquo;instar des fichiers PMSI en France) \u00e9taient encod\u00e9s sous forme de cha\u00eenes de longueur fixe sans s\u00e9parateur. Chaque colonne logique \u00e9tait d\u00e9finie par un intervalle de colonnes absolu : par exemple, le statut tabagique encod\u00e9 sur les positions 12 \u00e0 14, ou l&rsquo;indice de masse corporelle rapport\u00e9 entre les positions 15 et 18.<\/p>\n<p>La r\u00e8gle arithm\u00e9tique pour configurer la fonction <strong>SUBSTR<\/strong> dans ce cadre d\u00e9coule directement de la d\u00e9finition des bornes. Si l&rsquo;on souhaite capturer les caract\u00e8res situ\u00e9s entre la position de d\u00e9but <span class=\"arabpsy-math-inline\" data-latex=\"D\">$D$<\/span> et la position de fin <span class=\"arabpsy-math-inline\" data-latex=\"F\">$F$<\/span> (incluses), le deuxi\u00e8me argument de la fonction est trivialement <span class=\"arabpsy-math-inline\" data-latex=\"D\">$D$<\/span>, tandis que le troisi\u00e8me argument <span class=\"arabpsy-math-inline\" data-latex=\"n\">$n$<\/span> doit imp\u00e9rativement \u00eatre calcul\u00e9 selon la formule :<\/p>\n<p><code>n = F - D + 1<\/code><\/p>\n<p>Toute erreur dans ce calcul d&rsquo;amplitude entra\u00eene un d\u00e9calage de phase qui pollue l&rsquo;information recueillie en y incorporant un caract\u00e8re adjacent ou en omettant le caract\u00e8re terminal.<\/p>\n<figure class=\"wpt-preserved-image\"><img loading=\"lazy\" decoding=\"async\" src=\"http:\/\/french.arabpsychology.com\/wp-content\/uploads\/2026\/09\/substr2.jpg\" alt=\"\" \/><\/figure>\n<h3>4.2 Application programmatique dans un Data Step SAS<\/h3>\n<p>Illustrons cette m\u00e9thodologie par l&rsquo;extraction d&rsquo;une sous-cha\u00eene m\u00e9diane au sein d&rsquo;une variable d&rsquo;inventaire de laboratoire biom\u00e9dical. Supposons une cha\u00eene d&rsquo;identification d&rsquo;\u00e9chantillon biologique standardis\u00e9e formul\u00e9e ainsi : \u00ab\u00a0SER-B042-2023\u00a0\u00bb, o\u00f9 les trois premiers caract\u00e8res indiquent la nature du pr\u00e9l\u00e8vement (S\u00e9rum), les caract\u00e8res 5 \u00e0 8 d\u00e9signent la r\u00e9f\u00e9rence de la bo\u00eete de stockage cryog\u00e9nique, et les caract\u00e8res 10 \u00e0 13 indiquent l&rsquo;ann\u00e9e de mise en biobanque. L&rsquo;objectif est d&rsquo;isoler la r\u00e9f\u00e9rence de la bo\u00eete (\u00ab\u00a0B042\u00a0\u00bb) sans retenir le s\u00e9parateur tiret.<\/p>\n<p>Dans l&rsquo;\u00e9tape DATA, l&rsquo;op\u00e9ration se programme selon le sch\u00e9ma suivant :<\/p>\n<ul>\n<li>L&rsquo;indice de d\u00e9part <span class=\"arabpsy-math-inline\" data-latex=\"D\">$D$<\/span> est la position 5 (le caract\u00e8re \u00ab\u00a0B\u00a0\u00bb).<\/li>\n<li>L&rsquo;indice de fin <span class=\"arabpsy-math-inline\" data-latex=\"F\">$F$<\/span> est la position 8 (le caract\u00e8re \u00ab\u00a02\u00a0\u00bb).<\/li>\n<li>Le nombre de caract\u00e8res \u00e0 extraire est <span class=\"arabpsy-math-inline\" data-latex=\"8 - 5 + 1 = 4\">$8 &#8211; 5 + 1 = 4$<\/span>.<\/li>\n<li>L&rsquo;instruction s&rsquo;\u00e9crit formellement : <code>boite_id = SUBSTR(code_echantillon, 5, 4);<\/code>.<\/li>\n<\/ul>\n<p>Apr\u00e8s ex\u00e9cution de l&rsquo;\u00e9tape DATA et v\u00e9rification par une proc\u00e9dure <code>PROC PRINT<\/code> assortie de l&rsquo;option <code>DATA=...; RUN;<\/code>, la variable <code>boite_id<\/code> appara\u00eet sous une forme parfaitement calibr\u00e9e. Cette extraction m\u00e9diane permet de proc\u00e9der \u00e0 des agr\u00e9gations de donn\u00e9es par bo\u00eete de stockage (via PROC FREQ ou PROC SQL) afin de quantifier les taux de remplissage des cong\u00e9lateurs ultra-basse temp\u00e9rature, sans devoir alt\u00e9rer la variable d&rsquo;origine qui conserve l&rsquo;int\u00e9gralit\u00e9 de sa tra\u00e7abilit\u00e9 institutionnelle.<\/p>\n<h3>4.3 Implications analytiques lors de donn\u00e9es textuelles h\u00e9t\u00e9rog\u00e8nes<\/h3>\n<p>La vuln\u00e9rabilit\u00e9 majeure de l&rsquo;extraction par plage fixe m\u00e9diane r\u00e9side dans son intransigeance face \u00e0 l&rsquo;h\u00e9t\u00e9rog\u00e9n\u00e9it\u00e9 des donn\u00e9es d&rsquo;entr\u00e9e. D\u00e8s lors que la cha\u00eene de caract\u00e8res sous-jacente pr\u00e9sente une variabilit\u00e9 morphologique \u2014 par exemple si certains identifiants omettent des z\u00e9ros non significatifs, passant d&rsquo;un identifiant \u00ab\u00a0SER-B042-2023\u00a0\u00bb \u00e0 \u00ab\u00a0SER-B42-2023\u00a0\u00bb \u2014 la structure positionnelle s&rsquo;effondre. L&rsquo;appel strict \u00e0 la position 5 avec une largeur de 4 capturera alors \u00ab\u00a0B42-\u00ab\u00a0, incorporant ind\u00fbment le tiret de s\u00e9paration et corrompant la nomenclature.<\/p>\n<p>Face \u00e0 des bases de donn\u00e9es r\u00e9elles o\u00f9 la qualit\u00e9 de saisie n&rsquo;a pas \u00e9t\u00e9 verrouill\u00e9e par des masques stricts, l&rsquo;utilisation aveugle de <strong>SUBSTR<\/strong> \u00e0 positions fixes est une source majeure de biais analytiques non d\u00e9tect\u00e9s. Si la base est soumise \u00e0 des r\u00e9gressions statistiques ult\u00e9rieures, des modalit\u00e9s cat\u00e9gorielles fictives (comme \u00ab\u00a0B42-\u00ab\u00a0) appara\u00eetront dans les tableaux de contingence, dispersant la variance et diminuant la puissance statistique des tests d&rsquo;hypoth\u00e8se.<\/p>\n<p>Pour pr\u00e9venir ces \u00e9cueils, le statisticien doit imp\u00e9rativement d\u00e9ployer des contr\u00f4les de coh\u00e9rence pr\u00e9liminaires. Ces strat\u00e9gies incluent la v\u00e9rification pr\u00e9alable de la conformit\u00e9 de la longueur globale via l&rsquo;expression <code>IF LENGTH(variable) = 13 THEN ...<\/code>, ou la validation de la pr\u00e9sence des s\u00e9parateurs aux positions attendues. Si les longueurs des segments varient, l&rsquo;analyste devra abandonner l&rsquo;indexation absolue de <strong>SUBSTR<\/strong> au profit de m\u00e9thodes semi-dynamiques couplant <strong>SUBSTR<\/strong> avec la fonction <code>INDEX<\/code> ou <code>FIND<\/code>, ou basculer vers la fonction <code>SCAN<\/code> qui d\u00e9coupe le texte selon des balises s\u00e9paratrices ind\u00e9pendamment du nombre de glyphes intercalaires.<\/p>\n<h2>5. M\u00e9thode 3 : Extraction dynamique des N derniers caract\u00e8res<\/h2>\n<h3>5.1 Calcul dynamique du point d&rsquo;ancrage final via la fonction LENGTH<\/h3>\n<p>L&rsquo;extraction des caract\u00e8res situ\u00e9s \u00e0 la terminaison d&rsquo;une cha\u00eene \u2014 commun\u00e9ment appel\u00e9e extraction de suffixe \u2014 pr\u00e9sente une complexit\u00e9 algorithmique sup\u00e9rieure \u00e0 celle des pr\u00e9fixes. Dans la majorit\u00e9 des bases de donn\u00e9es r\u00e9elles, les cha\u00eenes de caract\u00e8res ne poss\u00e8dent pas toutes une dimension strictement uniforme. Si l&rsquo;on souhaite extraire les trois derniers caract\u00e8res de cha\u00eenes telles que \u00ab\u00a0TEST\u00a0\u00bb, \u00ab\u00a0EVALUATION\u00a0\u00bb ou \u00ab\u00a0MESURE\u00a0\u00bb, le point d&rsquo;ancrage de d\u00e9but ne peut pas \u00eatre une constante num\u00e9rique cod\u00e9e en dur. Il doit \u00eatre calcul\u00e9 de fa\u00e7on dynamique pour chaque observation qui transite par le PDV.<\/p>\n<p>Le fondement th\u00e9orique de cette extraction dynamique repose sur le calcul de la position de d\u00e9part \u00e0 l&rsquo;aide de la fonction de m\u00e9tadonn\u00e9e textuelle <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https:\/\/documentation.sas.com\/?docsetId=lefunctionsref&#038;docsetTarget=p0u7i2jeb44186n18c3pmsrt4h17.htm&#038;docsetVersion=9.4\">LENGTH<\/a>. La fonction <code>LENGTH(variable)<\/code> retourne l&rsquo;indice du dernier caract\u00e8re non blanc de la variable sp\u00e9cifi\u00e9e. Soit <span class=\"arabpsy-math-inline\" data-latex=\"L\">$L$<\/span> cette longueur effective et <span class=\"arabpsy-math-inline\" data-latex=\"N\">$N$<\/span> le nombre de caract\u00e8res constitutifs du suffixe souhait\u00e9. La position de d\u00e9part <span class=\"arabpsy-math-inline\" data-latex=\"P\">$P$<\/span> de l&rsquo;extraction terminale r\u00e9pond \u00e0 l&rsquo;\u00e9quation diff\u00e9rentielle suivante :<\/p>\n<p><code>P = L - N + 1<\/code><\/p>\n<p>Pourquoi ajouter 1 \u00e0 cette diff\u00e9rence arithm\u00e9tique ? Une omission classique consiste \u00e0 poser simplement <span class=\"arabpsy-math-inline\" data-latex=\"P = L - N\">$P = L &#8211; N$<\/span>. Si l&rsquo;on applique cette formule erron\u00e9e \u00e0 une cha\u00eene de longueur 10 pour extraire les 3 derniers caract\u00e8res, on obtiendrait <span class=\"arabpsy-math-inline\" data-latex=\"10 - 3 = 7\">$10 &#8211; 3 = 7$<\/span>. Or, les positions extraites seraient alors 7, 8 et 9, ce qui omettrait le dixi\u00e8me et dernier caract\u00e8re ! L&rsquo;ajout de l&rsquo;unit\u00e9 permet de restaurer l&rsquo;inclusivit\u00e9 des bornes, garantissant que la fen\u00eatre de longueur <span class=\"arabpsy-math-inline\" data-latex=\"N\">$N$<\/span> couvre exactement les indices allant de <span class=\"arabpsy-math-inline\" data-latex=\"L - N + 1\">$L &#8211; N + 1$<\/span> jusqu&rsquo;\u00e0 <span class=\"arabpsy-math-inline\" data-latex=\"L\">$L$<\/span>.<\/p>\n<figure class=\"wpt-preserved-image\"><img loading=\"lazy\" decoding=\"async\" src=\"http:\/\/french.arabpsychology.com\/wp-content\/uploads\/2026\/09\/substr3.jpg\" alt=\"\" \/><\/figure>\n<h3>5.2 D\u00e9veloppement du script SAS et traitement des suffixes<\/h3>\n<p>Mettons en pratique ce formalisme dynamique dans un script SAS con\u00e7u pour extraire les trois derniers caract\u00e8res d&rsquo;une s\u00e9rie de codes de s\u00e9v\u00e9rit\u00e9 clinique de longueurs h\u00e9t\u00e9rog\u00e8nes. Consid\u00e9rons des enregistrements contenant des cha\u00eenes comme \u00ab\u00a0URG-SEV-HIGH\u00a0\u00bb, \u00ab\u00a0OBS-NORMAL\u00a0\u00bb, ou \u00ab\u00a0INT-EXT-LOW\u00a0\u00bb :<\/p>\n<p>La formulation rigoureuse au sein du bloc DATA s&rsquo;ex\u00e9cute ainsi :<\/p>\n<ul>\n<li>\u00c9limination pr\u00e9alable de tout espace parasite terminal \u00e0 l&rsquo;aide de la fonction <code>STRIP<\/code> afin de fiabiliser la mesure.<\/li>\n<li>Calcul de la longueur s\u00e9mantique : <code>longueur_reelle = LENGTH(STRIP(code_clinique));<\/code>.<\/li>\n<li>D\u00e9termination de l&rsquo;indice de d\u00e9part : <code>pos_debut = longueur_reelle - 3 + 1;<\/code>.<\/li>\n<li>Application de la fonction : <code>suffixe = SUBSTR(code_clinique, pos_debut, 3);<\/code>.<\/li>\n<\/ul>\n<p>Il est possible de condenser l&rsquo;ensemble de cette cha\u00eene computationnelle en une unique instruction compacte :<\/p>\n<p><code>suffixe = SUBSTR(code_clinique, LENGTH(STRIP(code_clinique)) - 2);<\/code><\/p>\n<p>Notez ici une astuce syntaxique particuli\u00e8rement \u00e9l\u00e9gante permise par SAS : l&rsquo;omission d\u00e9lib\u00e9r\u00e9e du troisi\u00e8me param\u00e8tre <code>n<\/code>. D\u00e8s lors que la position de d\u00e9part est correctement calcul\u00e9e pour d\u00e9marrer exactement \u00e0 <span class=\"arabpsy-math-inline\" data-latex=\"N\">$N$<\/span> caract\u00e8res de la fin, ne pas renseigner le troisi\u00e8me argument ordonne \u00e0 SAS de capturer l&rsquo;ensemble du reliquat textuel jusqu&rsquo;au bout de la cha\u00eene. Cela all\u00e8ge consid\u00e9rablement l&rsquo;\u00e9criture tout en \u00e9liminant les redondances dans l&rsquo;expression.<\/p>\n<h3>5.3 Sc\u00e9narios complexes d&rsquo;extraction de suffixes<\/h3>\n<p>L&rsquo;extraction dynamique de suffixes est expos\u00e9e \u00e0 un risque computationnel majeur : le cas o\u00f9 la cha\u00eene examin\u00e9e s&rsquo;av\u00e8re plus courte que l&rsquo;amplitude <span class=\"arabpsy-math-inline\" data-latex=\"N\">$N$<\/span> requise. Si une observation contient la valeur \u00ab\u00a0AB\u00a0\u00bb (longueur effective = 2) et que l&rsquo;algorithme applique aveugl\u00e9ment la formule pour extraire 3 caract\u00e8res, le calcul de la position donne :<\/p>\n<p><code>P = 2 - 3 + 1 = 0<\/code><\/p>\n<p>Comme stipul\u00e9 dans la section syntaxique, un argument de position nul (<span class=\"arabpsy-math-inline\" data-latex=\"P = 0\">$P = 0$<\/span>) est strictement invalide dans SAS. L&rsquo;interpr\u00e9teur de l&rsquo;\u00e9tape DATA g\u00e9n\u00e9rera imm\u00e9diatement un avertissement dans le log (<code>NOTE: Invalid second argument to function SUBSTR at line...<\/code>), affectera une valeur manquante au r\u00e9sultat et incr\u00e9mentera le compteur d&rsquo;erreurs d&rsquo;ex\u00e9cution <code>_ERROR_ = 1<\/code>. Si ce probl\u00e8me survient sur des millions de lignes, le journal d&rsquo;ex\u00e9cution sera inond\u00e9 de messages d&rsquo;erreurs, ralentissant significativement les performances du serveur et invalidant l&rsquo;audit de qualification du traitement.<\/p>\n<p>Pour parer \u00e0 ce risque dans un cadre industriel ou acad\u00e9mique certifi\u00e9, il est indispensable de mettre en place une structure de garde conditionnelle (<em>defensive programming<\/em>). Le calcul ne doit \u00eatre d\u00e9clench\u00e9 que si et seulement si la cha\u00eene d&rsquo;origine dispose d&rsquo;une masse critique suffisante :<\/p>\n<ul>\n<li>V\u00e9rification pr\u00e9alable : <code>IF LENGTH(STRIP(chaine)) &gt;= 3 THEN suffixe = SUBSTR(STRIP(chaine), LENGTH(STRIP(chaine)) - 2);<\/code><\/li>\n<li>Prise en charge de l&rsquo;exception : <code>ELSE suffixe = chaine;<\/code> (ou affectation d&rsquo;une cha\u00eene sp\u00e9ciale d&rsquo;erreur comme \u00ab\u00a0N\/A\u00a0\u00bb).<\/li>\n<\/ul>\n<p>Ce blindage algorithmique assure une imperm\u00e9abilit\u00e9 totale du script face aux donn\u00e9es atypiques, pr\u00e9servant la propret\u00e9 du journal SAS et la continuit\u00e9 des traitements automatis\u00e9s.<\/p>\n<h2>6. M\u00e9thode 4 : Cr\u00e9ation conditionnelle de variables bas\u00e9es sur SUBSTR<\/h2>\n<h3>6.1 Combinaison logique des instructions IF-THEN\/ELSE et SUBSTR<\/h3>\n<p>L&rsquo;une des manifestations les plus puissantes de la fonction <strong>SUBSTR<\/strong> r\u00e9side dans son imbrication au sein d&rsquo;arborescences logiques conditionnelles. Plut\u00f4t que de simplement stocker une sous-cha\u00eene dans une nouvelle variable de transport, l&rsquo;analyste utilise souvent l&rsquo;extraction comme un test pr\u00e9dicatif \u00e0 l&rsquo;int\u00e9rieur d&rsquo;instructions <code>IF-THEN \/ ELSE<\/code>. La sous-cha\u00eene extraite est alors \u00e9valu\u00e9e \u00e0 la vol\u00e9e par rapport \u00e0 une constante litt\u00e9rale afin de piloter la cr\u00e9ation de variables d\u00e9riv\u00e9es dichotomiques, cat\u00e9gorielles ou de score.<\/p>\n<p>Sur le plan formel, la syntaxe prend la configuration g\u00e9n\u00e9rale suivante :<\/p>\n<p><code>IF SUBSTR(variable, position, n) = 'motif' THEN nouvelle_var = valeur_1; ELSE nouvelle_var = valeur_2;<\/code><\/p>\n<p>Cette approche est couramment employ\u00e9e pour op\u00e9rationnaliser des ph\u00e9notypes cliniques ou des typologies sociologiques \u00e0 partir de nomenclatures internationales. Dans les bases de donn\u00e9es d&rsquo;assurance maladie utilisant la <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https:\/\/icd.who.int\">Classification Internationale des Maladies (CIM-10)<\/a>, les diagnostics sont codifi\u00e9s par des cha\u00eenes alphanum\u00e9riques structur\u00e9es. Tous les codes de pathologies cardiovasculaires d\u00e9butent par la lettre \u00ab\u00a0I\u00a0\u00bb (de I00 \u00e0 I99), tandis que les n\u00e9oplasmes d\u00e9butent par \u00ab\u00a0C\u00a0\u00bb ou \u00ab\u00a0D\u00a0\u00bb. \u00c9valuer <code>IF SUBSTR(diagnostic, 1, 1) = 'I'<\/code> permet d&rsquo;instancier instantan\u00e9ment un indicateur binaire de risque cardiovasculaire pour chaque patient sans devoir charger des tables d&rsquo;\u00e9quivalences dictionnaires complexes.<\/p>\n<h3>6.2 D\u00e9monstration empirique sur le jeu de donn\u00e9es<\/h3>\n<p>Prenons un exemple empirique concret issu d&rsquo;une enqu\u00eate \u00e9pid\u00e9miologique sur la sant\u00e9 respiratoire. Supposons une table contenant un identifiant composite de participant nomm\u00e9 <code>id_dossier<\/code>, d&rsquo;une longueur de 8 caract\u00e8res. La convention m\u00e9thodologique impose que le sixi\u00e8me caract\u00e8re indique le groupe d&rsquo;exposition environnementale : \u00ab\u00a0T\u00a0\u00bb pour le groupe T\u00e9moin (non expos\u00e9 aux solvants), \u00ab\u00a0E\u00a0\u00bb pour le groupe Expos\u00e9 professionnellement, et \u00ab\u00a0D\u00a0\u00bb pour une exposition Douteuse ou non confirm\u00e9e.<\/p>\n<p>Le Data Step de traitement op\u00e9rationnel se structure comme suit :<\/p>\n<ul>\n<li>Initialisation de la longueur de la variable cible pour \u00e9viter toute troncature : <code>LENGTH statut_exposition $12;<\/code>.<\/li>\n<li>D\u00e9ploiement de la logique conditionnelle :\n<ul>\n<li><code>IF SUBSTR(id_dossier, 6, 1) = 'E' THEN statut_exposition = 'Expos\u00e9';<\/code><\/li>\n<li><code>ELSE IF SUBSTR(id_dossier, 6, 1) = 'T' THEN statut_exposition = 'T\u00e9moin';<\/code><\/li>\n<li><code>ELSE IF SUBSTR(id_dossier, 6, 1) = 'D' THEN statut_exposition = 'Ind\u00e9termin\u00e9';<\/code><\/li>\n<li><code>ELSE statut_exposition = 'Non r\u00e9pertori\u00e9';<\/code><\/li>\n<\/ul>\n<\/li>\n<li>Validation empirique par le biais d&rsquo;un tableau crois\u00e9 bidimensionnel g\u00e9n\u00e9r\u00e9 via <code>PROC FREQ; TABLES id_dossier * statut_exposition \/ LIST MISSING; RUN;<\/code>.<\/li>\n<\/ul>\n<p>Cette m\u00e9thodologie d&rsquo;assignation directe garantit que chaque observation est rigoureusement ventil\u00e9e au sein d&rsquo;une cat\u00e9gorie s\u00e9mantique intelligible pour les rapports finaux. Elle pr\u00e9vient les erreurs de reclassification manuelle et offre une lisibilit\u00e9 maximale pour les auditeurs de l&rsquo;\u00e9tude.<\/p>\n<h3>6.3 Complexification des filtres logiques conditionnels<\/h3>\n<p>Dans les environnements analytiques complexes, les pr\u00e9dicats fond\u00e9s sur <strong>SUBSTR<\/strong> doivent fr\u00e9quemment s&rsquo;articuler avec des op\u00e9rateurs logiques multiples (<code>AND<\/code>, <code>OR<\/code>, <code>IN<\/code>) ou s&rsquo;ins\u00e9rer au sein de structures d&#8217;embranchement plus performantes telles que les blocs <code>SELECT-WHEN<\/code>. L&rsquo;op\u00e9rateur <code>IN<\/code> se r\u00e9v\u00e8le particuli\u00e8rement pertinent lorsque l&rsquo;on recherche une sous-cha\u00eene appartenant \u00e0 un ensemble discret de modalit\u00e9s :<\/p>\n<p><code>IF SUBSTR(code, 1, 2) IN ('A1', 'A2', 'B5') THEN groupe_risque = '\u00c9lev\u00e9';<\/code><\/p>\n<p>De surcro\u00eet, la sensibilit\u00e9 \u00e0 la casse (majuscules versus minuscules) constitue une source fr\u00e9quente de faux n\u00e9gatifs dans l&rsquo;\u00e9valuation des conditions textuelles. Dans les moteurs de base de donn\u00e9es SAS, &lsquo;a&rsquo; est strictement distinct de &lsquo;A&rsquo;. Si un identifiant a \u00e9t\u00e9 encod\u00e9 par m\u00e9garde sous la forme \u00ab\u00a0e\u00a0\u00bb minuscule au lieu de \u00ab\u00a0E\u00a0\u00bb, la condition d&rsquo;\u00e9galit\u00e9 stricte \u00e9chouera silencieusement, faisant basculer \u00e0 tort l&rsquo;observation dans la branche r\u00e9siduelle <code>ELSE<\/code>.<\/p>\n<p>La standardisation syst\u00e9matique par les fonctions d&rsquo;homog\u00e9n\u00e9isation typographique s&rsquo;av\u00e8re donc indispensable. En encapsulant le premier argument de <strong>SUBSTR<\/strong> \u00e0 l&rsquo;int\u00e9rieur de la fonction <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https:\/\/documentation.sas.com\/?docsetId=lefunctionsref&#038;docsetTarget=p0s7y1kndc6uypn16tghf0l4z6q0.htm&#038;docsetVersion=9.4\">UPCASE<\/a> :<\/p>\n<p><code>IF SUBSTR(UPCASE(id_dossier), 6, 1) = 'E' THEN ...<\/code><\/p>\n<p>l&rsquo;analyste immunise son code contre toute variabilit\u00e9 typographique involontaire. Enfin, lors du traitement d&rsquo;arborescences de segmentation \u00e9tendues comprenant des dizaines de modalit\u00e9s, l&#8217;emploi de l&rsquo;instruction <code>SELECT (SUBSTR(id_dossier, 1, 2)); WHEN ('01') ... WHEN ('02') ... OTHERWISE ...; END;<\/code> offre un gain de lisibilit\u00e9 consid\u00e9rable et une optimisation notable des branchements compil\u00e9s par rapport \u00e0 une succession d\u00e9sordonn\u00e9e de clauses <code>IF-THEN-ELSE<\/code> imbriqu\u00e9es.<\/p>\n<h2>7. Utilisation avanc\u00e9e : SUBSTR en tant que pseudo-variable de remplacement<\/h2>\n<h3>7.1 Le concept de SUBSTR positionn\u00e9 \u00e0 gauche du signe \u00e9gal<\/h3>\n<p>L&rsquo;une des propri\u00e9t\u00e9s les plus remarquables \u2014 et pourtant souvent m\u00e9connue des praticiens de niveau interm\u00e9diaire \u2014 de la fonction <strong>SUBSTR<\/strong> est sa capacit\u00e9 \u00e0 intervenir \u00e0 la fois comme une fonction de lecture classique (\u00e0 droite du signe d&rsquo;\u00e9galit\u00e9) et comme une pseudo-variable de modification en m\u00e9moire (positionn\u00e9e \u00e0 gauche du signe d&rsquo;\u00e9galit\u00e9). Dans ce second cas, on parle formellement de <em>SUBSTR (left-hand side)<\/em> ou d&rsquo;assignation par sous-cha\u00eene.<\/p>\n<p>La syntaxe de cette construction s&rsquo;\u00e9tablit ainsi :<\/p>\n<p><code>SUBSTR(variable_cible, position, n) = 'nouvelle_valeur';<\/code><\/p>\n<p>Sur le plan de l&rsquo;architecture d&rsquo;ex\u00e9cution de SAS, ce positionnement modifie radicalement le comportement du compilateur. Au lieu de lire une s\u00e9quence d&rsquo;octets pour en instancier une copie dans un nouvel espace m\u00e9moire du PDV, l&rsquo;interpr\u00e9teur SAS acc\u00e8de directement au tampon m\u00e9moire allou\u00e9 \u00e0 la <code>variable_cible<\/code> et r\u00e9\u00e9crit physiquement les octets situ\u00e9s entre l&rsquo;indice <code>position<\/code> et l&rsquo;indice <code>position + n - 1<\/code> avec le contenu de la cha\u00eene fournie \u00e0 droite. Cette r\u00e9\u00e9criture s&rsquo;op\u00e8re en place (<em>in-place update<\/em>), sans cr\u00e9er de variable interm\u00e9diaire et sans n\u00e9cessiter de fastidieuses op\u00e9rations de concat\u00e9nation de segments amont et aval.<\/p>\n<figure class=\"wpt-preserved-image\"><img loading=\"lazy\" decoding=\"async\" src=\"http:\/\/french.arabpsychology.com\/wp-content\/uploads\/2026\/09\/substr4.jpg\" alt=\"\" \/><\/figure>\n<h3>7.2 Cas pratiques de substitution et d&rsquo;anonymisation de donn\u00e9es<\/h3>\n<p>Cette sp\u00e9cificit\u00e9 op\u00e9rationnelle de <strong>SUBSTR<\/strong> trouve une application directe et strat\u00e9gique dans les processus d&rsquo;anonymisation et de pseudonymisation des donn\u00e9es conform\u00e9ment aux r\u00e9glementations de protection de la vie priv\u00e9e (telles que le <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https:\/\/www.cnil.fr\/fr\/reglement-europeen-protection-donnees\">RGPD en Europe<\/a> ou l&rsquo;HIPAA aux \u00c9tats-Unis). Dans le cadre de cohortes de recherche en psychiatrie ou en addictologie, il est fr\u00e9quent que les donn\u00e9es brutes contiennent des num\u00e9ros d&rsquo;identification nationale de s\u00e9curit\u00e9 sociale ou des num\u00e9ros d&rsquo;enregistrement hospitalier qu&rsquo;il est ill\u00e9gal de diffuser en clair aux \u00e9quipes de recherche bio-informatique.<\/p>\n<p>Supposons une variable <code>identifiant_patient<\/code> d&rsquo;une longueur de 10 caract\u00e8res, telle que \u00ab\u00a0HOSP987654\u00a0\u00bb. Le comit\u00e9 d&rsquo;\u00e9thique impose que les six chiffres du milieu soient occult\u00e9s par des caract\u00e8res de masquage (\u00ab\u00a0XXXXXX\u00a0\u00bb) tout en pr\u00e9servant le pr\u00e9fixe de l&rsquo;\u00e9tablissement (\u00ab\u00a0HOSP\u00a0\u00bb) et le dernier chiffre de contr\u00f4le de cl\u00e9 (\u00ab\u00a04\u00a0\u00bb). Plut\u00f4t que de mobiliser des fonctions complexes de concat\u00e9nation, l&rsquo;analyste ex\u00e9cute une seule instruction d&rsquo;une limpidit\u00e9 absolue :<\/p>\n<p><code>SUBSTR(identifiant_patient, 5, 6) = 'XXXXXX';<\/code><\/p>\n<p>Cette commande cible exactement le segment num\u00e9rique m\u00e9dian et le remplace par les masques textuels. La variable r\u00e9sultante conserve strictement sa longueur originelle de 10 octets, son type primitif et ses attributs de format, tout en garantissant une anonymisation irr\u00e9versible des dossiers sans mobiliser la moindre ressource m\u00e9moire suppl\u00e9mentaire.<\/p>\n<h3>7.3 R\u00e8gles strictes et limitations de la pseudo-variable SUBSTR<\/h3>\n<p>L&rsquo;utilisation de <strong>SUBSTR<\/strong> en tant que pseudo-variable d&rsquo;affectation est r\u00e9gie par des r\u00e8gles d&rsquo;int\u00e9grit\u00e9 strictes dont la violation produit des r\u00e9sultats inattendus. La premi\u00e8re r\u00e8gle concerne la concordance entre le param\u00e8tre de longueur <code>n<\/code> et la taille physique de la cha\u00eene de remplacement fournie \u00e0 droite de l&rsquo;op\u00e9rateur d&rsquo;\u00e9galit\u00e9 :<\/p>\n<ul>\n<li>Si la cha\u00eene de remplacement est <strong>plus courte<\/strong> que la valeur de <code>n<\/code>, SAS \u00e9crit la cha\u00eene de remplacement puis comble le reste de la fen\u00eatre d&rsquo;\u00e9criture de taille <code>n<\/code> avec des espaces de remplissage (blanks). Les caract\u00e8res pr\u00e9existants situ\u00e9s dans cette fen\u00eatre sont alors irr\u00e9m\u00e9diablement \u00e9cras\u00e9s par ces espaces blancs.<\/li>\n<li>Si la cha\u00eene de remplacement est <strong>plus longue<\/strong> que la valeur de <code>n<\/code>, SAS tronque silencieusement la cha\u00eene de remplacement pour n&rsquo;injecter que ses <code>n<\/code> premiers caract\u00e8res dans la cible. Les caract\u00e8res en exc\u00e8s sont ignor\u00e9s sans qu&rsquo;aucune erreur ne soit lev\u00e9e.<\/li>\n<\/ul>\n<p>De plus, il est formellement impossible par ce m\u00e9canisme d&rsquo;\u00e9tendre la longueur physique globale allou\u00e9e \u00e0 la variable cible. Si une variable a \u00e9t\u00e9 d\u00e9clar\u00e9e avec une taille de 8 octets, l&rsquo;\u00e9criture <code>SUBSTR(var, 7, 5) = 'ABCDE';<\/code> provoquera une erreur d&rsquo;ex\u00e9cution dans le journal car l&rsquo;intervalle d&rsquo;\u00e9criture <span class=\"arabpsy-math-inline\" data-latex=\"[7; 11]\">$[7; 11]$<\/span> d\u00e9passe la borne physique absolue de 8 octets configur\u00e9e dans le PDV. L&rsquo;utilisation de <strong>SUBSTR<\/strong> \u00e0 gauche requiert donc une ma\u00eetrise g\u00e9om\u00e9trique parfaite des limites physiques pr\u00e9existantes de la variable \u00e0 modifier.<\/p>\n<h2>8. Comparaison fonctionnelle : SUBSTR face aux fonctions SCAN, INDEX et TRANWRD<\/h2>\n<h3>8.1 SUBSTR versus SCAN : D\u00e9coupage positionnel versus d\u00e9coupage par d\u00e9limiteur<\/h3>\n<p>Au sein de la bo\u00eete \u00e0 outils textuels de SAS, la distinction entre les fonctions <strong>SUBSTR<\/strong> et <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https:\/\/documentation.sas.com\/?docsetId=lefunctionsref&#038;docsetTarget=p16238b6o3i9p7n124q77a2u216w.htm&#038;docsetVersion=9.4\">SCAN<\/a> constitue l&rsquo;un des arbitrages m\u00e9thodologiques les plus fondamentaux. Ces deux op\u00e9rateurs r\u00e9solvent des probl\u00e9matiques de segmentation mais reposent sur des axiomes conceptuels radicalement diff\u00e9rents :<\/p>\n<table border=\"1\" cellpadding=\"6\" cellspacing=\"0\" style=\"border-collapse: collapse;width: 100%;margin-top: 15px;margin-bottom: 15px\">\n<thead>\n<tr style=\"background-color: #f2f2f2;text-align: left\">\n<th>Crit\u00e8re de comparaison<\/th>\n<th>Fonction SUBSTR<\/th>\n<th>Fonction SCAN<\/th>\n<\/tr>\n<\/thead>\n<tbody>\n<tr>\n<td><strong>Principe sous-jacent<\/strong><\/td>\n<td>D\u00e9coupage positionnel par coordonn\u00e9es absolues ou relatives.<\/td>\n<td>D\u00e9coupage lexical bas\u00e9 sur l&rsquo;occurrence de d\u00e9limiteurs.<\/td>\n<\/tr>\n<tr>\n<td><strong>Sensibilit\u00e9 \u00e0 la taille des mots<\/strong><\/td>\n<td>Tr\u00e8s \u00e9lev\u00e9e : toute variation de taille fausse l&rsquo;extraction.<\/td>\n<td>Nulle : extrait le mot complet quelle que soit son amplitude.<\/td>\n<\/tr>\n<tr>\n<td><strong>Gestion des s\u00e9parateurs multiples<\/strong><\/td>\n<td>Ne g\u00e8re pas les s\u00e9parateurs ; extrait les d\u00e9limiteurs s&rsquo;ils sont dans la fen\u00eatre.<\/td>\n<td>Traite les s\u00e9ries cons\u00e9cutives de d\u00e9limiteurs comme une fronti\u00e8re unique.<\/td>\n<\/tr>\n<tr>\n<td><strong>Performance CPU<\/strong><\/td>\n<td>Maximale : lecture directe du pointeur m\u00e9moire sans parsing.<\/td>\n<td>L\u00e9g\u00e8rement inf\u00e9rieure : n\u00e9cessite un scan s\u00e9quentiel des octets.<\/td>\n<\/tr>\n<tr>\n<td><strong>Cas d&rsquo;usage pr\u00e9f\u00e9rentiel<\/strong><\/td>\n<td>Donn\u00e9es \u00e0 colonnes fixes, identifiants standardis\u00e9s codifi\u00e9s.<\/td>\n<td>Listes d&rsquo;adresses, textes narratifs, r\u00e9ponses en langage naturel.<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<p>Le choix de l&rsquo;une ou l&rsquo;autre d\u00e9pend donc directement de la nature structurelle des donn\u00e9es. Si une variable pr\u00e9sente la forme standardis\u00e9e \u00ab\u00a0ABC-123-XY\u00a0\u00bb, <strong>SUBSTR<\/strong> est parfaitement appropri\u00e9e. En revanche, si la cha\u00eene pr\u00e9sente la forme d&rsquo;une liste de pathologies d&rsquo;un patient s\u00e9par\u00e9es par des virgules (\u00ab\u00a0Asthme, Diab\u00e8te de type 2, Hypertension\u00a0\u00bb), o\u00f9 la longueur de chaque mot est par nature impr\u00e9visible, l&rsquo;utilisation de <strong>SUBSTR<\/strong> m\u00e8nerait \u00e0 une impasse m\u00e9thodologique, tandis que <code>SCAN(liste, 2, ',')<\/code> extraira avec \u00e9l\u00e9gance le second diagnostic (\u00ab\u00a0Diab\u00e8te de type 2\u00a0\u00bb).<\/p>\n<h3>8.2 Compl\u00e9mentarit\u00e9 avec INDEX, FIND et LENGTH<\/h3>\n<p>Bien que <strong>SUBSTR<\/strong> soit fondamentalement positionnelle, son potentiel s&rsquo;accro\u00eet de mani\u00e8re exponentielle lorsqu&rsquo;elle est combin\u00e9e avec les fonctions de recherche textuelle telles que <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https:\/\/documentation.sas.com\/?docsetId=lefunctionsref&#038;docsetTarget=p1h284r6l9v8m8n1b7r7o2m8f2a1.htm&#038;docsetVersion=9.4\">INDEX<\/a> et <code>FIND<\/code>. Ces fonctions retournent l&rsquo;indice num\u00e9rique exact de la premi\u00e8re occurrence d&rsquo;un motif ou d&rsquo;un caract\u00e8re sp\u00e9cifique au sein d&rsquo;une cha\u00eene cible.<\/p>\n<p>Consid\u00e9rons une situation o\u00f9 l&rsquo;on doit extraire une s\u00e9quence num\u00e9rique d\u00e9butant imm\u00e9diatement apr\u00e8s un mot-cl\u00e9 sp\u00e9cifique (par exemple \u00ab\u00a0REF:\u00a0\u00bb) au sein d&rsquo;une variable textuelle libre. La position de ce mot-cl\u00e9 varie d&rsquo;une observation \u00e0 l&rsquo;autre. Le couplage fonctionnel permet de cr\u00e9er une extraction semi-dynamique adaptative :<\/p>\n<ul>\n<li>Localisation de la balise : <code>pos_balise = FIND(texte_brut, 'REF:');<\/code>.<\/li>\n<li>D\u00e9termination du point d&rsquo;entr\u00e9e : <code>pos_debut = pos_balise + LENGTH('REF:');<\/code>.<\/li>\n<li>Extraction robuste : <code>IF pos_balise &gt; 0 THEN ref_extraite = SUBSTR(texte_brut, pos_debut, 6);<\/code>.<\/li>\n<\/ul>\n<p>Ce patron d&rsquo;architecture logicielle (<em>design pattern<\/em>) conf\u00e8re \u00e0 <strong>SUBSTR<\/strong> la flexibilit\u00e9 contextuelle qui lui manquait \u00e0 l&rsquo;origine, tout en conservant son avantage d&rsquo;extraction pr\u00e9cise de largeur fixe une fois le rep\u00e8re dynamique localis\u00e9.<\/p>\n<h3>8.3 SUBSTR face \u00e0 TRANWRD et aux expressions r\u00e9guli\u00e8res (PRX)<\/h3>\n<p>Lorsque la t\u00e2che programmatique implique le remplacement d&rsquo;un segment de cha\u00eene, l&rsquo;arbitrage s&rsquo;op\u00e8re entre <strong>SUBSTR<\/strong> (c\u00f4t\u00e9 gauche), la fonction <code>TRANWRD<\/code> (Translate Word) et les fonctions d&rsquo;expressions r\u00e9guli\u00e8res issues du moteur Perl (notamment <code>PRXCHANGE<\/code>).<\/p>\n<p>La fonction <code>TRANWRD(source, 'ancien', 'nouveau')<\/code> op\u00e8re un balayage global de la cha\u00eene pour remplacer syst\u00e9matiquement toutes les occurrences du motif cibl\u00e9 par un nouveau motif, avec la possibilit\u00e9 d&rsquo;alt\u00e9rer la longueur globale de la cha\u00eene. En comparaison, l&rsquo;assignation via <strong>SUBSTR<\/strong> ne modifie que la position pr\u00e9cis\u00e9ment d\u00e9sign\u00e9e, sans toucher \u00e0 d&rsquo;\u00e9ventuelles occurrences identiques situ\u00e9es ailleurs. <strong>SUBSTR<\/strong> sera donc pr\u00e9f\u00e9r\u00e9e pour une modification chirurgicale cibl\u00e9e, tandis que <code>TRANWRD<\/code> convient \u00e0 une substitution th\u00e9matique globale.<\/p>\n<p>Quant aux expressions r\u00e9guli\u00e8res (<code>PRXPARSE<\/code>, <code>PRXMATCH<\/code>, <code>PRXCHANGE<\/code>), elles offrent la puissance de la th\u00e9orie des automates finis pour reconna\u00eetre des motifs complexes (adresses \u00e9lectroniques, s\u00e9quences g\u00e9nomiques avec tol\u00e9rance d&rsquo;erreur, structures syntaxiques floues). Cependant, cette flexibilit\u00e9 s&rsquo;accompagne d&rsquo;un co\u00fbt computationnel substantiel en termes de cycles d&rsquo;horloge CPU. Pour une extraction \u00e0 structure fixe d\u00e9terministe, mobiliser un moteur d&rsquo;expressions r\u00e9guli\u00e8res Perl repr\u00e9sente un surco\u00fbt algorithmique inutile. <strong>SUBSTR<\/strong> s&rsquo;av\u00e8re entre 10 et 50 fois plus rapide qu&rsquo;un appel PRX \u00e9quivalent lors du traitement de volum\u00e9tries massives de plusieurs dizaines de millions d&rsquo;enregistrements.<\/p>\n<h2>9. Gestion des espaces, encodages et sp\u00e9cificit\u00e9s de la fonction SUBSTRN<\/h2>\n<h3>9.1 Comportement face aux cha\u00eenes courtes et introduction de SUBSTRN<\/h3>\n<p>L&rsquo;une des limitations historiques de la fonction classique <strong>SUBSTR<\/strong> r\u00e9side dans son intransigeance face aux d\u00e9passements d&rsquo;indices. Si le param\u00e8tre <code>position<\/code> est sup\u00e9rieur \u00e0 la longueur de la cha\u00eene, ou si l&rsquo;amplitude <code>n<\/code> sollicit\u00e9e s&rsquo;\u00e9tend au-del\u00e0 de la terminaison physique de la cha\u00eene, SAS g\u00e9n\u00e8re un message d&rsquo;erreur d&rsquo;ex\u00e9cution dans le journal et renvoie une valeur manquante. Dans des pipelines de production automatis\u00e9s, l&rsquo;apparition de ces messages peut bloquer les contr\u00f4les d&rsquo;int\u00e9grit\u00e9 ou alerter inutilement les syst\u00e8mes de supervision automatique.<\/p>\n<p>Pour rem\u00e9dier \u00e0 cette rigidit\u00e9 syntaxique, SAS a introduit \u00e0 partir de la version 9 la fonction <strong>SUBSTRN<\/strong>. La signature formelle et le r\u00f4le de <strong>SUBSTRN<\/strong> sont identiques \u00e0 ceux de <strong>SUBSTR<\/strong>, \u00e0 une diff\u00e9rence fondamentale pr\u00e8s : son comportement face aux conditions aux limites (<em>boundary conditions<\/em>). La fonction <strong>SUBSTRN<\/strong> g\u00e8re de fa\u00e7on permissive les param\u00e8tres hors limites :<\/p>\n<ul>\n<li>Si la position de d\u00e9part est sup\u00e9rieure \u00e0 la longueur de la cha\u00eene source, <strong>SUBSTRN<\/strong> retourne une cha\u00eene vide de longueur z\u00e9ro sans lever le moindre avertissement d&rsquo;erreur dans le journal.<\/li>\n<li>Si la somme de la position de d\u00e9part et de l&rsquo;amplitude <span class=\"arabpsy-math-inline\" data-latex=\"n\">$n$<\/span> exc\u00e8de la taille totale de la cha\u00eene h\u00f4te, <strong>SUBSTRN<\/strong> extrait simplement l&rsquo;ensemble des caract\u00e8res restants jusqu&rsquo;au terme de la cha\u00eene sans g\u00e9n\u00e9rer d&rsquo;erreur d&rsquo;argument invalide.<\/li>\n<li>Si l&rsquo;argument d&rsquo;amplitude <span class=\"arabpsy-math-inline\" data-latex=\"n\">$n$<\/span> est \u00e9valu\u00e9 \u00e0 0, <strong>SUBSTRN<\/strong> renvoie une cha\u00eene vide, alors que <strong>SUBSTR<\/strong> l\u00e8verait une erreur.<\/li>\n<\/ul>\n<p>Dans tous les contextes d&rsquo;ingestion de donn\u00e9es textuelles non pr\u00e9alablement nettoy\u00e9es, l&rsquo;utilisation syst\u00e9matique de <strong>SUBSTRN<\/strong> constitue une pratique recommand\u00e9e pour immuniser les scripts contre les arr\u00eats inopin\u00e9s tout en \u00e9vitant la pollution du journal d&rsquo;ex\u00e9cution.<\/p>\n<h3>9.2 Interaction avec les fonctions de nettoyage TRIM, STRIP et COMPBL<\/h3>\n<p>L&rsquo;exactitude des calculs de position dans <strong>SUBSTR<\/strong> est intimement corr\u00e9l\u00e9e \u00e0 l&rsquo;\u00e9tat de propret\u00e9 des espaces au sein de la cha\u00eene d&rsquo;origine. Les fonctions d&rsquo;assainissement textuel doivent agir comme des pr\u00e9traitements m\u00e9thodologiques obligatoires :<\/p>\n<ul>\n<li><strong>STRIP(chaine)<\/strong> : Supprime imp\u00e9rativement les espaces initiaux (\u00e0 gauche) et les espaces finaux (\u00e0 droite). Elle est essentielle avant de mesurer la longueur effective via <code>LENGTH()<\/code> pour calibrer une extraction de fin de cha\u00eene.<\/li>\n<li><strong>COMPBL(chaine)<\/strong> : R\u00e9duit les s\u00e9quences d&rsquo;espaces multiples cons\u00e9cutifs situ\u00e9s \u00e0 l&rsquo;int\u00e9rieur de la cha\u00eene \u00e0 un seul et unique espace standard. Si un identifiant composite utilise l&rsquo;espace comme s\u00e9parateur interne (\u00ab\u00a0CENTRE 01 DOSSIER 12\u00a0\u00bb), des doubles espaces accidentels d\u00e9caleraient l&rsquo;ensemble des indices absolus en aval ; l&rsquo;application de <code>COMPBL<\/code> restaure l&rsquo;homog\u00e9n\u00e9it\u00e9 g\u00e9om\u00e9trique du texte.<\/li>\n<\/ul>\n<p>Le tableau ci-dessous illustre l&rsquo;impact critique du nettoyage pr\u00e9alable des espaces sur le r\u00e9sultat d&rsquo;un appel \u00e0 <code>SUBSTR(chaine, 1, 4)<\/code> :<\/p>\n<table border=\"1\" cellpadding=\"6\" cellspacing=\"0\" style=\"border-collapse: collapse;width: 100%;margin-top: 15px;margin-bottom: 15px\">\n<thead>\n<tr style=\"background-color: #f2f2f2;text-align: left\">\n<th>Valeur brute de la cha\u00eene<\/th>\n<th>Appel direct : SUBSTR(chaine, 1, 4)<\/th>\n<th>Appel assaini : SUBSTR(STRIP(chaine), 1, 4)<\/th>\n<\/tr>\n<\/thead>\n<tbody>\n<tr>\n<td><code>\"DATA_01\"<\/code><\/td>\n<td><code>\"DATA\"<\/code> (Conforme)<\/td>\n<td><code>\"DATA\"<\/code> (Conforme)<\/td>\n<\/tr>\n<tr>\n<td><code>\" DATA_01\"<\/code> (1 espace en t\u00eate)<\/td>\n<td><code>\" DAT\"<\/code> (Tronqu\u00e9 \/ Invalide)<\/td>\n<td><code>\"DATA\"<\/code> (Corrig\u00e9 et Conforme)<\/td>\n<\/tr>\n<tr>\n<td><code>\"   DATA_01\"<\/code> (3 espaces en t\u00eate)<\/td>\n<td><code>\"   D\"<\/code> (Critique \/ Invalide)<\/td>\n<td><code>\"DATA\"<\/code> (Corrig\u00e9 et Conforme)<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<p>L&rsquo;int\u00e9gration de ce r\u00e9flexe d&rsquo;assainissement syst\u00e9matique (<code>STRIP<\/code>) pr\u00e9vient l&rsquo;\u00e9crasante majorit\u00e9 des anomalies de d\u00e9calage positionnel rencontr\u00e9es lors du d\u00e9ploiement de programmes en production.<\/p>\n<h3>9.3 Encodage des caract\u00e8res et consid\u00e9rations multioctets (DBCS \/ UTF-8)<\/h3>\n<p>Avec l&rsquo;internationalisation croissante de la recherche m\u00e9dicale et l&rsquo;adoption universelle du standard d&rsquo;encodage <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https:\/\/www.unicode.org\">Unicode UTF-8<\/a> dans les architectures modernes SAS Viya et SAS 9.4 sous Linux, une complexit\u00e9 fondamentale appara\u00eet : la dissociation entre la notion d&rsquo;<strong>octet (byte)<\/strong> et la notion de <strong>caract\u00e8re (glyphe typographique)<\/strong>.<\/p>\n<p>Historiquement, sous les encodages monooctets d&rsquo;Europe occidentale (comme LATIN1 ou WLATIN1), un caract\u00e8re \u00e9tait repr\u00e9sent\u00e9 de mani\u00e8re biunivoque par exactement un octet de 8 bits en m\u00e9moire. Dans cet \u00e9cosyst\u00e8me classique, <code>SUBSTR<\/code> coupait indiff\u00e9remment des octets ou des caract\u00e8res. En revanche, sous un encodage multioctet tel que l&rsquo;UTF-8, les caract\u00e8res accentu\u00e9s ou diacritiques propres \u00e0 la langue fran\u00e7aise (\u00e9, \u00e8, \u00ea, \u00e7, \u00e0), ainsi que les id\u00e9ogrammes asiatiques ou alphabets cyrilliques, sont encod\u00e9s sur une s\u00e9quence variable de deux, trois voire quatre octets.<\/p>\n<p>Si l&rsquo;on applique la fonction <strong>SUBSTR<\/strong> classique \u00e0 une cha\u00eene UTF-8 contenant le mot \u00ab\u00a0\u00c9VALUATION\u00a0\u00bb, o\u00f9 la lettre \u00ab\u00a0\u00c9\u00a0\u00bb majuscule est encod\u00e9e sur deux octets distincts (les octets hexad\u00e9cimaux <code>C3 89<\/code>) :<\/p>\n<p>L&rsquo;instruction <code>SUBSTR('\u00c9VALUATION', 1, 1)<\/code> ne collectera que le tout premier octet (<code>C3<\/code>). Cet octet isol\u00e9 ne constitue pas un caract\u00e8re Unicode valide ; il s&rsquo;agit d&rsquo;un fragment incomplet. Le r\u00e9sultat produit sera un caract\u00e8re corrompu (souvent mat\u00e9rialis\u00e9 par un point d&rsquo;interrogation ou le symbole de remplacement <code><\/code> dans l&rsquo;interface), et SAS pourra consigner un avertissement d&rsquo;encodage invalide.<\/p>\n<p>Pour garantir la portabilit\u00e9 internationale et la rigueur du traitement en encodage UTF-8, il est imp\u00e9ratif d&rsquo;utiliser la famille des fonctions nationales ou \u00e0 support de caract\u00e8res \u00e9tendus (fonctions <strong>K<\/strong>), sp\u00e9cifiquement la fonction <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https:\/\/documentation.sas.com\/?docsetId=lefunctionsref&#038;docsetTarget=n14z2304917j9en1vslz819k18f7.htm&#038;docsetVersion=9.4\">KSUBSTR<\/a>. La fonction <strong>KSUBSTR<\/strong> op\u00e8re en mesurant les indices en termes de <em>caract\u00e8res typographiques per\u00e7us<\/em> et non en octets physiques. Elle d\u00e9code pr\u00e9alablement la s\u00e9quence multioctet pour extraire fid\u00e8lement l&rsquo;int\u00e9gralit\u00e9 du glyphe Unicode sans scinder ses octets constitutifs. Cette pr\u00e9caution est devenue un standard incontournable dans les environnements de calcul haute performance contemporains.<\/p>\n<h2>10. Applications pratiques compl\u00e8tes sur donn\u00e9es de recherche empirique<\/h2>\n<h3>10.1 Cas pratique 1 : Parsing d&rsquo;identifiants de sujets dans un essai longitudinal<\/h3>\n<p>Consid\u00e9rons un protocole de recherche translationnelle longitudinale \u00e9valuant l&rsquo;efficacit\u00e9 d&rsquo;une immunoth\u00e9rapie cibl\u00e9e. La table source des inclusions hospitali\u00e8res agr\u00e8ge les donn\u00e9es administratives sous un code sujet consolid\u00e9 de 12 caract\u00e8res formul\u00e9 ainsi : <code>\"PAR02-C1-045A\"<\/code>. Ce code standardis\u00e9 condense quatre dimensions analytiques fondamentales :<\/p>\n<ul>\n<li>Les positions 1 \u00e0 3 : Trigramme du centre hospitalier (ex: \u00ab\u00a0PAR\u00a0\u00bb = H\u00f4pital Piti\u00e9-Salp\u00eatri\u00e8re).<\/li>\n<li>Les positions 4 et 5 : Num\u00e9ro du d\u00e9partement investigateur (ex: \u00ab\u00a002\u00a0\u00bb = Oncologie m\u00e9dicale).<\/li>\n<li>Les positions 7 et 8 : Num\u00e9ro de la cohorte d&rsquo;escalade de dose (ex: \u00ab\u00a0C1\u00a0\u00bb = Cohorte \u00e0 10mg\/kg).<\/li>\n<li>Les positions 10 \u00e0 12 : Num\u00e9ro d&rsquo;ordre chronologique d&rsquo;inclusion du sujet (ex: \u00ab\u00a0045\u00a0\u00bb).<\/li>\n<li>La position 13 : Statut du bras th\u00e9rapeutique (ex: \u00ab\u00a0A\u00a0\u00bb = Bras Actif, \u00ab\u00a0P\u00a0\u00bb = Bras Placebo).<\/li>\n<\/ul>\n<p>Le bloc DATA ci-dessous d\u00e9ploie l&rsquo;ing\u00e9nierie d&rsquo;extraction positionnelle garantissant la ventilation multi-colonnes en une seule passe de lecture s\u00e9quentielle :<\/p>\n<figure class=\"wpt-preserved-image\"><img loading=\"lazy\" decoding=\"async\" src=\"http:\/\/french.arabpsychology.com\/wp-content\/uploads\/2026\/09\/substr5.jpg\" alt=\"\" \/><\/figure>\n<p>Voici le d\u00e9roulement m\u00e9thodique du traitement :<\/p>\n<ul>\n<li>D\u00e9finition de l&rsquo;\u00e9tape DATA cr\u00e9ant la table normalis\u00e9e <code>COHORTE_PARSEE<\/code>.<\/li>\n<li>D\u00e9claration des longueurs cibles via l&rsquo;instruction <code>LENGTH<\/code> :\n<ul>\n<li><code>centre_id $3<\/code><\/li>\n<li><code>dept_id $2<\/code><\/li>\n<li><code>cohorte_code $2<\/code><\/li>\n<li><code>patient_num 8.<\/code> (pour transformation num\u00e9rique ult\u00e9rieure)<\/li>\n<li><code>bras_traitement $1<\/code><\/li>\n<\/ul>\n<\/li>\n<li>Ex\u00e9cution des extractions chirurgicales par la fonction <strong>SUBSTR<\/strong> :\n<ul>\n<li><code>centre_id = SUBSTR(code_sujet, 1, 3);<\/code><\/li>\n<li><code>dept_id = SUBSTR(code_sujet, 4, 2);<\/code><\/li>\n<li><code>cohorte_code = SUBSTR(code_sujet, 7, 2);<\/code><\/li>\n<li><code>patient_num = INPUT(SUBSTR(code_sujet, 10, 3), 3.);<\/code> (remarquez l&rsquo;imbrication imm\u00e9diate de la fonction <code>INPUT<\/code> pour convertir la sous-cha\u00eene textuelle de 3 caract\u00e8res en un entier num\u00e9rique r\u00e9el exploitable pour des tris chronologiques).<\/li>\n<li><code>bras_traitement = SUBSTR(code_sujet, 13, 1);<\/code><\/li>\n<\/ul>\n<\/li>\n<li>Contr\u00f4le de coh\u00e9rence : une instruction d&rsquo;assertion v\u00e9rifie la conformit\u00e9 : <code>IF bras_traitement NOT IN ('A', 'P') THEN PUT \"ALERTE: Statut bras invalide pour sujet \" code_sujet=;<\/code>.<\/li>\n<\/ul>\n<p>Ce programme s\u00e9pare les informations composites en entit\u00e9s atomiques relationnelles, permettant une tra\u00e7abilit\u00e9 totale des analyses de sous-groupes requises par les autorit\u00e9s r\u00e9glementaires de sant\u00e9 publique.<\/p>\n<h3>10.2 Cas pratique 2 : Extraction et scoring d&rsquo;une batterie d&rsquo;items psychom\u00e9triques<\/h3>\n<p>Dans les enqu\u00eates de sant\u00e9 comportementale ou d&rsquo;\u00e9pid\u00e9miologie psychiatrique, les instruments psychom\u00e9triques (tels que le <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https:\/\/www.apa.org\">CES-D pour la d\u00e9pression ou l&rsquo;\u00e9chelle d&rsquo;anxi\u00e9t\u00e9 STAI de Spielberger<\/a>) comportent souvent plusieurs dizaines de questions \u00e0 \u00e9chelle ordinale. Afin d&rsquo;\u00e9conomiser l&rsquo;espace r\u00e9seau et le stockage dans les syst\u00e8mes de saisie sur tablette en milieu hospitalier, les r\u00e9ponses d&rsquo;un patient \u00e0 un inventaire de 10 items sont compact\u00e9es en une unique s\u00e9quence dense de 10 chiffres continus (ex: \u00ab\u00a03142201324\u00a0\u00bb, chaque chiffre de 0 \u00e0 4 repr\u00e9sentant l&rsquo;intensit\u00e9 d&rsquo;un sympt\u00f4me ressenti).<\/p>\n<p>L&rsquo;enjeu m\u00e9thodologique consiste \u00e0 \u00e9clater cette cha\u00eene continue en 10 variables distinctes (<code>item_1<\/code> \u00e0 <code>item_10<\/code>) et \u00e0 calculer instantan\u00e9ment le score brut cumul\u00e9 du participant. Ce traitement peut \u00eatre \u00e9l\u00e9gamment automatis\u00e9 en associant la fonction <strong>SUBSTR<\/strong> \u00e0 une boucle it\u00e9rative <code>DO<\/code> et \u00e0 une structure vectorielle d&rsquo;<code>ARRAY<\/code> :<\/p>\n<p>L&rsquo;impl\u00e9mentation algorithmique se structure selon les \u00e9tapes suivantes :<\/p>\n<ul>\n<li>D\u00e9claration d&rsquo;un tableau num\u00e9rique de 10 \u00e9l\u00e9ments : <code>ARRAY items[10] item_1 - item_10;<\/code>.<\/li>\n<li>Initialisation de la variable de cumul : <code>score_brut = 0;<\/code>.<\/li>\n<li>Boucle de balayage it\u00e9ratif d&rsquo;indice <span class=\"arabpsy-math-inline\" data-latex=\"i\">$i$<\/span> allant de 1 \u00e0 10 :\n<ul>\n<li><code>DO i = 1 TO 10;<\/code><\/li>\n<li>Extraction de chaque caract\u00e8re individuel en position dynamique <span class=\"arabpsy-math-inline\" data-latex=\"i\">$i$<\/span> avec une largeur fixe de 1 : <code>char_item = SUBSTR(chaine_reponses, i, 1);<\/code>.<\/li>\n<li>Conversion de ce caract\u00e8re textuel en entier arithm\u00e9tique et affectation dans l&rsquo;\u00e9l\u00e9ment correspondant du tableau : <code>items[i] = INPUT(char_item, 1.);<\/code>.<\/li>\n<li>Agr\u00e9gation arithm\u00e9tique incr\u00e9mentale : <code>score_brut = score_brut + items[i];<\/code>.<\/li>\n<li>Fermeture de la boucle : <code>END;<\/code>.<\/li>\n<\/ul>\n<\/li>\n<li>Suppression de la variable temporaire d&rsquo;it\u00e9ration devenue inutile : <code>DROP i char_item;<\/code>.<\/li>\n<\/ul>\n<p>Gr\u00e2ce \u00e0 la synergie entre la boucle it\u00e9rative et l&rsquo;indice dynamique de <strong>SUBSTR<\/strong>, quelques lignes de code remplacent une suite fastidieuse de 10 assignations manuelles distinctes. Ce paradigme \u00e9limine tout risque d&rsquo;erreur de copier-coller dans la d\u00e9signation des positions et garantit une extensibilit\u00e9 parfaite si le questionnaire venait \u00e0 \u00eatre \u00e9tendu \u00e0 50 ou 100 items.<\/p>\n<h3>10.3 Cas pratique 3 : Reformatage et validation de dates alphanum\u00e9riques non conventionnelles<\/h3>\n<p>Un probl\u00e8me \u00e9pid\u00e9miologique classique d\u00e9coule de l&rsquo;h\u00e9t\u00e9rog\u00e9n\u00e9it\u00e9 des formats de dates issus de logiciels tiers ou de dossiers patients informatis\u00e9s obsol\u00e8tes. Les dates y sont fr\u00e9quemment enregistr\u00e9es sous forme de cha\u00eenes textuelles compactes non standardis\u00e9es par la norme ISO 8601, par exemple au format invers\u00e9 am\u00e9ricain compact : \u00ab\u00a020240315\u00a0\u00bb (Ann\u00e9e-Mois-Jour sans s\u00e9parateurs) ou \u00ab\u00a015032024\u00a0\u00bb (Jour-Mois-Ann\u00e9e). Pour effectuer des mod\u00e9lisations de survie via des mod\u00e8les de Cox (PROC PHREG), ces cha\u00eenes doivent imp\u00e9rativement \u00eatre converties en de v\u00e9ritables dates au format SAS standard (qui repr\u00e9sentent le nombre de jours \u00e9coul\u00e9s depuis le 1er janvier 1960).<\/p>\n<p>Pour une date brute sous format \u00ab\u00a0AAAAMMJJ\u00a0\u00bb (\u00ab\u00a020240315\u00a0\u00bb), la cha\u00eene doit \u00eatre diss\u00e9qu\u00e9e en ses trois composantes canoniques via la fonction <strong>SUBSTR<\/strong>, avant d&rsquo;\u00eatre r\u00e9assembl\u00e9e par la fonction calendaire <code>MDY<\/code> :<\/p>\n<ul>\n<li>Extraction de l&rsquo;ann\u00e9e (les 4 premiers caract\u00e8res) : <code>annee = INPUT(SUBSTR(date_brute, 1, 4), 4.);<\/code><\/li>\n<li>Extraction du mois (positions 5 et 6) : <code>mois = INPUT(SUBSTR(date_brute, 5, 2), 2.);<\/code><\/li>\n<li>Extraction du jour (positions 7 et 8) : <code>jour = INPUT(SUBSTR(date_brute, 7, 2), 2.);<\/code><\/li>\n<li>Reconstruction s\u00e9curis\u00e9e de la date SAS : <code>date_sas = MDY(mois, jour, annee);<\/code><\/li>\n<li>Application du format d&rsquo;affichage standardis\u00e9 : <code>FORMAT date_sas DATE9.;<\/code><\/li>\n<\/ul>\n<p>Cette approche permet \u00e9galement d&rsquo;intercaler des filtres de validation clinique. Si le sous-segment mois extrait par <code>SUBSTR<\/code> est \u00e9valu\u00e9 \u00e0 une valeur sup\u00e9rieure \u00e0 12 ou si le jour d\u00e9passe 31, l&rsquo;analyste peut intercepter l&rsquo;anomalie avant m\u00eame d&rsquo;appeler la fonction <code>MDY<\/code>, \u00e9vitant ainsi les erreurs de calcul calendaire dans le journal et isolant les dossiers m\u00e9dicaux d\u00e9faillants dans une table de rejet d&rsquo;audit.<\/p>\n<h2>11. Diagnostic des erreurs courantes et analyse du journal SAS (SAS Log)<\/h2>\n<h3>11.1 Identification et r\u00e9solution de l&rsquo;erreur &lsquo;Invalid second argument&rsquo;<\/h3>\n<p>L&rsquo;observation du journal d&rsquo;ex\u00e9cution (le <em>SAS Log<\/em>) constitue le barom\u00e8tre essentiel de l&rsquo;int\u00e9grit\u00e9 de vos programmes. L&rsquo;une des anomalies les plus couramment rencontr\u00e9es lors de l&rsquo;usage de <strong>SUBSTR<\/strong> se signale par l&rsquo;apparition de messages d&rsquo;avertissement st\u00e9r\u00e9otyp\u00e9s :<\/p>\n<p><code>NOTE: Invalid second argument to function SUBSTR at line X column Y.<\/code><\/p>\n<p>Ce message d&rsquo;alerte indique sans ambigu\u00eft\u00e9 que le param\u00e8tre <code>position<\/code> s&rsquo;est vu assigner une valeur incompatible avec les axiomes de la fonction lors du passage d&rsquo;une observation sp\u00e9cifique dans le PDV. Les causes racines de cette anomalie sont au nombre de trois :<\/p>\n<ul>\n<li>La position calcul\u00e9e est \u00e9gale \u00e0 0 ou n\u00e9gative (ce qui arrive typiquement lors d&rsquo;un calcul dynamique de suffixe mal calibr\u00e9 sur une cha\u00eene trop courte).<\/li>\n<li>La position est strictement sup\u00e9rieure \u00e0 la longueur d\u00e9clar\u00e9e ou effective de la variable textuelle source.<\/li>\n<li>La variable contenant l&rsquo;indice de position pr\u00e9sente une valeur manquante (num\u00e9rique <code>.<\/code>).<\/li>\n<\/ul>\n<p>Pour diagnostiquer rapidement l&rsquo;origine pr\u00e9cise de l&rsquo;erreur au sein d&rsquo;une table contenant plusieurs millions de lignes, l&rsquo;analyste doit instrumenter son code d&rsquo;une sonde de d\u00e9bogage conditionnelle utilisant l&rsquo;instruction <code>PUT<\/code> :<\/p>\n<p><code>IF position &lt;= 0 OR position &gt; LENGTH(chaine) THEN PUT \"ERREUR DIAGNOSTIC : ID=\" id_sujet \" CHAINE=\" chaine \" POS=\" position;<\/code><\/p>\n<p>Cette commande intercepte l&rsquo;observation d\u00e9viante avant l&rsquo;ex\u00e9cution de la fonction, imprime ses valeurs dans le journal pour investigation manuelle, et permet d&rsquo;\u00e9viter l&rsquo;\u00e9mission r\u00e9p\u00e9t\u00e9e des alertes du compilateur en appliquant un traitement de repli pr\u00e9ventif.<\/p>\n<h3>11.2 Probl\u00e8mes de troncature et gestion de la longueur implicite<\/h3>\n<p>Le second pi\u00e8ge m\u00e9thodologique majeur, d&rsquo;autant plus insidieux qu&rsquo;il ne produit <strong>aucune erreur visible dans le journal<\/strong>, concerne la troncature silencieuse r\u00e9sultant des r\u00e8gles de longueur implicite de SAS. Supposons le segment d&rsquo;instructions suivant :<\/p>\n<p><code>IF condition = 1 THEN code_groupe = SUBSTR(id_long, 1, 2);<br \/>\nELSE code_groupe = SUBSTR(id_long, 1, 5);<\/code><\/p>\n<p>Que se passe-t-il lors de la compilation de ce bloc ? SAS lit la premi\u00e8re ligne o\u00f9 la variable <code>code_groupe<\/code> est mentionn\u00e9e. Le premier appel \u00e0 <strong>SUBSTR<\/strong> poss\u00e8de une constante d&rsquo;amplitude de 2. Le compilateur en d\u00e9duit irr\u00e9vocablement que la variable <code>code_groupe<\/code> doit \u00eatre cr\u00e9\u00e9e avec une longueur physique de 2 octets dans le PDV. Lorsque, lors de l&rsquo;ex\u00e9cution, une observation satisfait la clause <code>ELSE<\/code>, le second appel extrait bien 5 caract\u00e8res, mais SAS est contraint de tronquer les 3 derniers caract\u00e8res pour faire entrer la donn\u00e9e dans la variable fig\u00e9e \u00e0 2 octets ! La variable contiendra alors \u00ab\u00a0AB\u00a0\u00bb au lieu de \u00ab\u00a0ABCDE\u00a0\u00bb, faussant int\u00e9gralement les segmentations statistiques subs\u00e9quentes sans que l&rsquo;analyste n&rsquo;en soit averti.<\/p>\n<p>La parade m\u00e9thodologique absolue, rappel\u00e9e avec insistance dans les standards de programmation de l&rsquo;<a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https:\/\/www.fda.gov\">US FDA pour les soumissions \u00e9lectroniques d&rsquo;essais cliniques<\/a>, consiste \u00e0 d\u00e9clarer de mani\u00e8re programmatique la longueur de toute variable nouvellement cr\u00e9\u00e9e par une instruction <code>LENGTH<\/code> prioritaire :<\/p>\n<p><code>LENGTH code_groupe $5;<\/code><\/p>\n<p>Plac\u00e9e avant toute instruction d&rsquo;assignation ou de test logique, cette d\u00e9claration force le compilateur \u00e0 dimensionner imm\u00e9diatement le PDV \u00e0 5 octets, neutralisant d\u00e9finitivement tout risque de troncature silencieuse lors des embranchements ult\u00e9rieurs.<\/p>\n<h3>11.3 Gestion des valeurs manquantes textuelles (Missing Values)<\/h3>\n<p>Un autre vecteur de vuln\u00e9rabilit\u00e9 r\u00e9side dans le comportement de <strong>SUBSTR<\/strong> lorsqu&rsquo;elle est confront\u00e9e \u00e0 une variable source dont le contenu est manquant (une cha\u00eene vide compos\u00e9e uniquement d&rsquo;espaces blancs). Selon la version de SAS et la formulation des param\u00e8tres, deux comportements sont observ\u00e9s :<\/p>\n<ul>\n<li>Si l&rsquo;extraction d\u00e9bute en position 1 avec une longueur d\u00e9finie <code>n<\/code>, SAS extrait simplement <code>n<\/code> espaces blancs et affecte une cha\u00eene manquante \u00e0 la variable r\u00e9ceptrice sans g\u00e9n\u00e9rer d&rsquo;erreur bloquante.<\/li>\n<li>En revanche, si l&rsquo;extraction repose sur un calcul dynamique utilisant la fonction <code>LENGTH()<\/code>, la situation se d\u00e9grade. Pour une cha\u00eene enti\u00e8rement manquante, la fonction <code>LENGTH(chaine)<\/code> renvoie conventionnellement la valeur 1 (en SAS classique). Le calcul d&rsquo;un suffixe sur 3 caract\u00e8res aboutit \u00e0 une position de d\u00e9part : <span class=\"arabpsy-math-inline\" data-latex=\"1 - 3 + 1 = -1\">$1 &#8211; 3 + 1 = -1$<\/span>. Une position n\u00e9gative d\u00e9clenche imm\u00e9diatement l&rsquo;interruption du calcul pour cette ligne et g\u00e9n\u00e8re une erreur d&rsquo;argument invalide dans le log.<\/li>\n<\/ul>\n<p>La r\u00e8gle d&rsquo;hygi\u00e8ne logicielle consiste donc \u00e0 encapsuler tout traitement textuel dynamique dans un test pr\u00e9liminaire de pr\u00e9sence via la fonction <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https:\/\/documentation.sas.com\/?docsetId=lefunctionsref&#038;docsetTarget=p1h4i0m5r0m8f2a1b7r7o2m8f2a1.htm&#038;docsetVersion=9.4\">MISSING<\/a> :<\/p>\n<p><code>IF NOT MISSING(chaine_source) THEN DO;<br \/>\n&nbsp;&nbsp;&nbsp;&nbsp;\/* Logique d'extraction avanc\u00e9e via SUBSTR *\/<br \/>\nEND;<br \/>\nELSE nouvelle_variable = '';<\/code><\/p>\n<p>Cette pr\u00e9caution \u00e9l\u00e9mentaire garantit que les observations incompl\u00e8tes traversent l&rsquo;\u00e9tape DATA sans d\u00e9stabiliser les calculs positionnels ni alt\u00e9rer les m\u00e9triques d&rsquo;audit d&rsquo;ex\u00e9cution.<\/p>\n<h2>12. Bonnes pratiques m\u00e9thodologiques, optimisation des performances et synth\u00e8se<\/h2>\n<h3>12.1 Optimisation des ressources lors du traitement de volum\u00e9tries massives<\/h3>\n<p>Dans l&rsquo;\u00e8re du <em>Big Data<\/em> en sant\u00e9 publique et des registres \u00e9pid\u00e9miologiques nationaux comprenant des centaines de millions d&rsquo;enregistrements (tels que les bases m\u00e9dico-administratives du SNDS en France), la question de l&#8217;empreinte m\u00e9moire et de l&rsquo;efficience des cycles processeur (CPU) devient pr\u00e9pond\u00e9rante. Bien que <strong>SUBSTR<\/strong> soit intrins\u00e8quement rapide, son usage non optimis\u00e9 peut entra\u00eener une d\u00e9gradation substantielle des temps de calcul.<\/p>\n<p>Le premier levier d&rsquo;optimisation concerne l&rsquo;allocation stricte de la m\u00e9moire vive. D\u00e9clarer une variable extraite avec une longueur g\u00e9n\u00e9reuse par d\u00e9faut (par exemple <code>$200<\/code>) au lieu de sa taille exacte (<code>$4<\/code>) gonfle inutilement la taille du bloc d&rsquo;enregistrement dans le PDV. Multipli\u00e9e par 50 millions d&rsquo;observations, cette allocation superflue augmente de plusieurs gigaoctets la taille physique de la table sur les disques de stockage, ralentit consid\u00e9rablement les op\u00e9rations d&rsquo;entr\u00e9es\/sorties (I\/O) et sature la m\u00e9moire cache des serveurs de traitement. Le dimensionnement au plus juste via l&rsquo;instruction <code>LENGTH<\/code> est donc un imp\u00e9ratif d&rsquo;optimisation financi\u00e8re et mat\u00e9rielle.<\/p>\n<p>Le second levier concerne l&rsquo;arbitrage entre <strong>SUBSTR<\/strong> et les expressions r\u00e9guli\u00e8res Perl (fonctions PRX). Les fonctions PRX n\u00e9cessitent l&rsquo;instanciation en m\u00e9moire d&rsquo;une machine \u00e0 \u00e9tats et la compilation d&rsquo;un automate d&rsquo;analyse syntaxique. Nos bancs de test comparatifs d\u00e9montrent que pour des op\u00e9rations de d\u00e9coupage positionnel \u00e9l\u00e9mentaire sur un volume de 20 millions de lignes, une \u00e9tape DATA exploitant <strong>SUBSTR<\/strong> s&rsquo;ex\u00e9cute en moyenne en <strong>3,2 secondes<\/strong> d&rsquo;horloge CPU, l\u00e0 o\u00f9 le pattern \u00e9quivalent formul\u00e9 avec <code>PRXCHANGE<\/code> ou <code>PRXPARSE<\/code> requiert plus de <strong>48 secondes<\/strong>. La simplicit\u00e9 g\u00e9om\u00e9trique de <strong>SUBSTR<\/strong> doit donc toujours \u00eatre privil\u00e9gi\u00e9e lorsque la structure textuelle est stable et d\u00e9terministe.<\/p>\n<h3>12.2 R\u00e8gles de codage d\u00e9fensif et lisibilit\u00e9 du code SAS<\/h3>\n<p>La maintenabilit\u00e9 \u00e0 long terme des programmes SAS en milieu acad\u00e9mique ou r\u00e9glement\u00e9 (GCP\/BPC) repose sur la clart\u00e9 documentaire du code source. Un appel cryptique tel que <code>val = SUBSTR(str, 8, 3);<\/code> oblige tout r\u00e9viseur ou auditeur externe \u00e0 replonger dans les dictionnaires de donn\u00e9es pour reconstituer le sens des indices 8 et 3.<\/p>\n<p>Pour transformer une programmation artisanale en un script r\u00e9pondant aux meilleurs standards de l&rsquo;ing\u00e9nierie logicielle, appliquez les recommandations suivantes :<\/p>\n<ul>\n<li><strong>Documentez explicitement les indices positionnels<\/strong> : Commentez syst\u00e9matiquement la signification des coordonn\u00e9es g\u00e9om\u00e9triques (ex: <code>\/* Extraction du code r\u00e9gion sanitaire (pos 8 \u00e0 10) *\/<\/code>).<\/li>\n<li><strong>Utilisez des macro-variables pour nommer les constantes de configuration<\/strong> : D\u00e9finir en amont <code>%LET DEBUT_ANNEE = 1; %LET LONG_ANNEE = 4;<\/code> puis \u00e9crire <code>SUBSTR(date, &amp;DEBUT_ANNEE, &amp;LONG_ANNEE)<\/code> rend le script auto-descriptif et modifiable en un unique point centralis\u00e9 si la sp\u00e9cification de format venait \u00e0 \u00e9voluer.<\/li>\n<li><strong>Standardisez les conventions de nommage des variables d\u00e9riv\u00e9es<\/strong> : Adoptez des suffixes ou pr\u00e9fixes explicites documentant l&rsquo;op\u00e9ration r\u00e9alis\u00e9e, par exemple en nommant la variable <code>site_cod_sub<\/code> ou <code>date_yr_extr<\/code>, \u00e9vitant ainsi toute ambigu\u00eft\u00e9 sur la nature d\u00e9riv\u00e9e de l&rsquo;information.<\/li>\n<\/ul>\n<h3>12.3 Synth\u00e8se et guide de d\u00e9cision pour les analystes de donn\u00e9es<\/h3>\n<p>Pour guider le praticien de donn\u00e9es dans ses choix d&rsquo;architecture programmatique, la matrice de d\u00e9cision ci-dessous r\u00e9sume les quatre grandes m\u00e9thodes d&rsquo;extraction abord\u00e9es dans ce document, leurs signatures canoniques et leurs domaines d&rsquo;\u00e9lection m\u00e9thodologique :<\/p>\n<table border=\"1\" cellpadding=\"6\" cellspacing=\"0\" style=\"border-collapse: collapse;width: 100%;margin-top: 15px;margin-bottom: 15px\">\n<thead>\n<tr style=\"background-color: #f2f2f2;text-align: left\">\n<th>M\u00e9thode d&rsquo;extraction<\/th>\n<th>Signature syntaxique type<\/th>\n<th>Conditions pr\u00e9requises<\/th>\n<th>Domaine d&rsquo;application id\u00e9al<\/th>\n<\/tr>\n<\/thead>\n<tbody>\n<tr>\n<td><strong>1. Extraction Pr\u00e9fixe<\/strong><\/td>\n<td><code>SUBSTR(chaine, 1, N)<\/code><\/td>\n<td>Cha\u00eene sans espaces initiaux (ou apr\u00e8s application de <code>STRIP<\/code>).<\/td>\n<td>Isolement d&rsquo;identifiants pays, codes centres, pr\u00e9fixes de protocoles.<\/td>\n<\/tr>\n<tr>\n<td><strong>2. Extraction Plage M\u00e9diane<\/strong><\/td>\n<td><code>SUBSTR(chaine, Debut, Largeur)<\/code><\/td>\n<td>Champs \u00e0 g\u00e9om\u00e9trie fixe et rigoureusement standardis\u00e9e.<\/td>\n<td>Parsing de fichiers PMSI, registres d&rsquo;\u00e9tat-civil, bases institutionnelles \u00e0 colonnes fixes.<\/td>\n<\/tr>\n<tr>\n<td><strong>3. Extraction Suffixe Dynamique<\/strong><\/td>\n<td><code>SUBSTR(STRIP(chaine), LENGTH(STRIP(chaine)) - N + 1)<\/code><\/td>\n<td>V\u00e9rification que <code>LENGTH(chaine) &gt;= N<\/code> pour \u00e9viter les erreurs d&rsquo;indice n\u00e9gatif.<\/td>\n<td>R\u00e9cup\u00e9ration de codes d&rsquo;\u00e9tat finaux, extensions de fichiers, cl\u00e9s de contr\u00f4le terminales.<\/td>\n<\/tr>\n<tr>\n<td><strong>4. \u00c9valuation Conditionnelle<\/strong><\/td>\n<td><code>IF SUBSTR(chaine, Pos, N) = 'VAL' THEN ...<\/code><\/td>\n<td>Standardisation pr\u00e9alable de la casse typographique (<code>UPCASE<\/code>).<\/td>\n<td>Segmentation clinique, stratification \u00e9pid\u00e9miologique, cr\u00e9ation d&rsquo;indicateurs de risque.<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<p>En perspective d&rsquo;avenir, il convient de souligner que les principes fondamentaux de la fonction <strong>SUBSTR<\/strong> demeurent d&rsquo;une parfaite continuit\u00e9 au sein des nouvelles architectures de traitement massivement parall\u00e8les <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https:\/\/support.sas.com\/resources\/papers\/proceedings17\/SAS0431-2017.pdf\">SAS Viya et du langage DS2<\/a>. Bien que le langage DS2 introduise des concepts orient\u00e9s objet et une gestion native des types de donn\u00e9es SQL modernes (tels que VARCHAR ou NCHAR), la logique de l&rsquo;indexation de sous-cha\u00eenes par coordonn\u00e9es y conserve toute sa pertinence algorithmique. En assimilant les r\u00e8gles syntaxiques, les implications de compilation et les strat\u00e9gies de blindage d\u00e9fensif expos\u00e9es dans cette monographie, vous disposez d&rsquo;un socle d&rsquo;expertise p\u00e9renne pour garantir la robustesse, la reproductibilit\u00e9 et l&rsquo;excellence scientifique de l&rsquo;ensemble de vos analyses de donn\u00e9es textuelles.<\/p>\n<h2>R\u00e9f\u00e9rences<\/h2>\n<ul>\n<li>American Psychological Association. (2020). <em>Publication Manual of the American Psychological Association<\/em> (7th ed.). American Psychological Association. https:\/\/doi.org\/10.1037\/0000165-000<\/li>\n<li>Clinical Data Interchange Standards Consortium. (2021). <em>Study Data Tabulation Model Implementation Guide (SDTMIG) for Human Clinical Trials<\/em> (Version 3.3). CDISC. https:\/\/www.cdisc.org\/standards\/foundational\/sdtmig<\/li>\n<li>Commission Nationale de l&rsquo;Informatique et des Libert\u00e9s. (2018). <em>R\u00e8glement g\u00e9n\u00e9ral sur la protection des donn\u00e9es (RGPD) : Guide pour les professionnels<\/em>. CNIL. https:\/\/www.cnil.fr\/fr\/reglement-europeen-protection-donnees<\/li>\n<li>Food and Drug Administration. (2022). <em>Data Standards Manual: Study Data Specifications<\/em>. U.S. Department of Health and Human Services. https:\/\/www.fda.gov\/industry\/fda-data-standards-advisory-board\/study-data-standards-resources<\/li>\n<li>SAS Institute Inc. (2020). <em>SAS(R) 9.4 Functions and CALL Routines: Reference<\/em> (5th ed.). SAS Institute Inc. https:\/\/documentation.sas.com\/?docsetId=lefunctionsref&amp;docsetTarget=titlepage.htm&amp;docsetVersion=9.4<\/li>\n<li>SAS Institute Inc. (2021). <em>SAS(R) Viya(R) Programming Documentation: DS2 Language Reference<\/em>. SAS Institute Inc. https:\/\/documentation.sas.com\/?docsetId=ds2ref&amp;docsetTarget=titlepage.htm&amp;docsetVersion=v_001<\/li>\n<li>The Unicode Consortium. (2023). <em>The Unicode Standard, Version 15.0<\/em>. Unicode Consortium. https:\/\/www.unicode.org\/versions\/Unicode15.0.0\/<\/li>\n<li>World Health Organization. (2019). <em>International Statistical Classification of Diseases and Related Health Problems<\/em> (11th ed.). World Health Organization. https:\/\/icd.who.int\/<\/li>\n<\/ul>\n","protected":false},"excerpt":{"rendered":"<p>Guide m\u00e9thodologique complet pour ma\u00eetriser la fonction SUBSTR dans SAS : extraction de texte, syntaxe fondamentale, manipulation conditionnelle et exemples pratiques.<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"closed","template":"","categories":[1829,9499],"tags":[10221,10234,3002,235,11321],"class_list":["post-9898","psych_stat","type-psych_stat","status-publish","hentry","category-methodologie-statistique","category-programmation-sas","tag-data-step","tag-manipulation-de-chaines","tag-nettoyage-de-donnees","tag-sas","tag-substr"],"_links":{"self":[{"href":"https:\/\/french.arabpsychology.com\/index.php?rest_route=\/wp\/v2\/psych_stat\/9898","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/french.arabpsychology.com\/index.php?rest_route=\/wp\/v2\/psych_stat"}],"about":[{"href":"https:\/\/french.arabpsychology.com\/index.php?rest_route=\/wp\/v2\/types\/psych_stat"}],"author":[{"embeddable":true,"href":"https:\/\/french.arabpsychology.com\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/french.arabpsychology.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=9898"}],"version-history":[{"count":1,"href":"https:\/\/french.arabpsychology.com\/index.php?rest_route=\/wp\/v2\/psych_stat\/9898\/revisions"}],"predecessor-version":[{"id":9904,"href":"https:\/\/french.arabpsychology.com\/index.php?rest_route=\/wp\/v2\/psych_stat\/9898\/revisions\/9904"}],"wp:attachment":[{"href":"https:\/\/french.arabpsychology.com\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=9898"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/french.arabpsychology.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=9898"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/french.arabpsychology.com\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=9898"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}