Stéganographie à double lettre


19

La stéganographie cache un message donné à l'intérieur d'un support donné, produisant un paquet qui ne semble pas suspect. Pour ce défi, vous allez écrire un programme qui prend en entrée un message ASCII et un support ASCII, et retourner ou imprimer un package identique au support sauf que les caractères correspondant au message sont doublés, dans le même ordre qu'ils apparaissent dans le message.

Règles:

  1. Si le support contient déjà plusieurs séquences du même caractère et qu'elles ne sont pas utilisées pour coder un caractère du message, le programme les réduira à un seul caractère.
  2. Si le transporteur ne contient pas les caractères du message dans le bon ordre, le programme peut ne rien retourner, le transporteur lui-même ou une erreur.
  3. Vous pouvez supposer que le message et le support sont des chaînes ASCII non vides.
  4. Questions de capitalisation: A n'est pas équivalent à a.
  5. Lorsque plusieurs packages sont valides, votre programme peut générer tout ou partie d'entre eux.
  6. L'espace est un personnage comme tout autre personnage.

Cas de test:

Forfait porteur de messages
"salut" "est-il arrivé?" "est-il arrivé?" OU "est-ce qu'il est arrivé?"
"monsieur" "est-il arrivé?" "est-il arrivé?"
"foo" "est-il arrivé?" "" OU "est-il arrivé?" OU une erreur.
"Voiture" "Les chats sont cool." "CCaats arre col."
"voiture" "Les chats sont cool." "" OU "Les chats sont cool." OU une erreur.
"Canapé" "Canapé" "CCoouucchh"
"oo" "oooooooooo" "oooo"
"o o" "oooo oooa" "oo ooa"

C'est le golf de code, donc le moins d'octets gagne.


5
Pas du tout suspect ...: P
Quintec

Est-ce que "oooo oa"(avec 2 espaces) une sortie valide pour le dernier cas de test?
Arnauld

3
Ce n'est pas une sortie valide car l'ordre des caractères doublés dans le package doit correspondre à l'ordre des caractères dans le message. Dans le message, nous avons un «o», puis un «», puis un «o», mais votre paquet a l'espace après les o
jkpate

Ah oui, ça a du sens.
Arnauld

1
Non. Mon raisonnement derrière cette règle est que la sortie du programme en cas d'absence de solution doit être sans équivoque qu'aucune solution n'est possible. Les trois sorties autorisées sont sans ambiguïté, mais une vérification plus approfondie serait nécessaire pour le cas dédupliqué.
jkpate

Réponses:


5

Gelée , 28 octets

ẹⱮŒp<ƝẠ$ƇṪ
nƝ+çṬ¥a⁸ḟ0Ḥç¦ð¹ç?

Un programme complet prenant carrieret en messagetant qu'arguments de ligne de commande qui imprime le résultat
(pour un non-packable messageimprime inchangé carrier).

Essayez-le en ligne! Ou consultez la suite de tests .

Comment?

ẹⱮŒp<ƝẠ$ƇṪ - Link 1, helper function to find the indices to double: carrier, message
           -                               e.g. "programming", "rom"
 Ɱ         - map across message with:
ẹ          -   indices of                       [[2,5], [3], [7,8]]
  Œp       - Cartesian product                  [[2,3,7],[2,3,8],[5,3,7],[5,3,8]]
        Ƈ  - filter keep if:
       $   -   last two links as a monad:
     Ɲ     -     for neighbours:
    <      -       less than?                    [1,1]   [1,1]   [0,1]   [0,1]
      Ạ    -     all truthy?                     1       1       0       0
           -                                    [[2,3,7],[2,3,8]]
         Ṫ - tail (if empty yields 0)                    [2,3,8]

nƝ+çṬ¥a⁸ḟ0Ḥç¦ð¹ç? - Main Link: carrier, message
                ? - if...
               ç  - ...condition: last Link (the helper function) as a dyad
             ð    - ...then: perform the dyadic chain to the left (described below)
              ¹   - ...else: do nothing (yields carrier)
                  - (the then clause:)
 Ɲ                - for neighbours in the carrier
n                 - not equal?
     ¥            - last two links as a dyad:
   ç              -   call last Link (the helper function) as a dyad
    Ṭ             -   untruth (e.g. [2,5] -> [0,1,0,0,1])
  +               - add (vectorises)
      a⁸          - logical AND with carrier
        ḟ0        - filter out zeros
            ¦     - sparse application...
           ç      - ...to indices: call last Link (the helper function) as a dyad
          Ḥ       - ...do: double (e.g. 'x' -> 'xx')

3

JavaScript (ES6), 71 octets

Prend l'entrée comme (message)(carrier).

s=>g=([c,...C],p)=>c?(c==s[0]?(s=s.slice(1),c)+c:p==c?'':c)+g(C,c):s&&X

Essayez-le en ligne!


Version alternative, 66 octets

Si nous pouvons prendre le message comme un tableau de caractères:

s=>g=([c,...C],p)=>c?(c==s[0]?s.shift()+c:p==c?'':c)+g(C,c):s+s&&X

Essayez-le en ligne!


Edit : Merci à @tsh d'avoir remarqué que j'ai oublié de supprimer du code lors du passage des versions non récursives aux versions récursives.


Vous pouvez supprimer p=car p est passé par un paramètre.
tsh

@tsh Oups. C'est du code résiduel des versions précédentes non récursives que j'ai oublié de supprimer. Je vous remercie!
Arnauld

2

Haskell, 124 121 107 107 101 97 95 90 octets

(#).(++"ü")
"ü"#[]=[]
p@(m:n)#e@(c:d)|m/=c=c:p#snd(span(==c)d)|m==n!!0=m:m:n#d|1<2=m:n#e

Déclenche l'exception "Modèles non exhaustifs" si le transporteur ne contient pas le message.

Essayez-le en ligne!

Edit: -5 octets grâce à @Laikoni.


Je pense que changer les cas vous permet de laisser tomber m==c: Essayez-le en ligne!
Laikoni

1

Retina 0.8.2 , 67 octets

+`(.)(\1*)\1*(.*¶)(?(\1)(\1(\2)))(.*)$(?!¶)
$1$4$5¶$3$6
M!s`.*¶$
¶

Essayez-le en ligne! Prend le transporteur sur la première ligne et le message sur la deuxième ligne. Explication:

+`(.)(\1*)\1*(.*¶)(?(\1)(\1(\2)))(.*)$(?!¶)
$1$4$5¶$3$6

Traite les exécutions de 1 ou plusieurs caractères identiques du support. S'il existe également une séquence de 1 ou plusieurs des mêmes caractères dans le message, ajoutez la plus courte des deux séquences à la sortie en double, sinon ajoutez un seul caractère de la porteuse à la sortie. Chaque série de caractères de sortie se termine par une nouvelle ligne pour la distinguer de l'entrée. Le (?!¶)à la fin empêche l'expression régulière de penser que le transporteur est le message une fois que le message est épuisé, comme il $est normalement autorisé de correspondre à l'endroit où ¶$il correspondrait.

M!s`.*¶$

Supprimez tout si le message n'était pas complètement codé.

Supprimez les retours à la ligne de la sortie.


Je pense qu'il ne passe pas l'avant-dernier cas de test (ce qui, pour être honnête, je ne l'avais pas dans le post initial).
jkpate

@jkpate Merci d'avoir signalé cela; J'ai dû réécrire légèrement mon approche.
Neil

0

Nettoyer , 118 octets

import StdEnv,StdLib
$[][]=[]
$[u:v]b#(_,w)=span((==)u)v
|b%(0,0)==[u]=[u,u: $if(v%(0,0)<>b%(1,1))w v(tl b)]=[u: $w b]

Essayez-le en ligne!

Prend d'abord le transporteur, puis le message.

Erreurs avec Run time error, rule '$;2' in module 'main' does not matchsi le message ne rentre pas.


0

Rubis , 73 octets

f=->m,c,b=p{x,*c=c;x ?(x==m[0]?x+m.shift: x==b ?'':x)+f[m,c,x]:m[0]?x:''}

Essayez-le en ligne!

Fonction récursive, prend les entrées sous forme de tableau de caractères.

Pour une fois, j'espérais utiliser la squeezeméthode intégrée de Ruby qui contracte des exécutions consécutives du même personnage à une seule instance. Mais malheureusement, non - les deux derniers cas de test ont tout si mal tourné, que j'ai dû recourir à une approche complètement différente, et cela s'est avéré être essentiellement un portage de la réponse d' Arnauld .


0

Powershell, 134 octets

param($m,$c)$c-csplit"([$m])"|%{$i+=$o=$_-ceq$m[+$i]
if($o-or$_-cne"`0$h"[-1]){$h+=($_-replace'(.)(?=\1)')*($o+1)}}
$h*!($i-$m.Length)

Le script renvoie le empty stringsi le transporteur ne contient pas les caractères du message dans le bon ordre.

Script de test moins golfé:

$f = {

param($message,$carrier)
$carrier-csplit"([$message])"|%{                # split by chars of the message, chars itself included ([])
    $offset=$_-ceq$message[+$i]                 # 0 or 1 if current substring is a current message char (case-sensitive equality)
    $i+=$offset                                 # move to next message char if need it
    if($offset-or$_-cne"`0$h"[-1]){             # condition to remove redundant doubles after message char: arrrived -> arrived, ooo -> oo, etc
                                                # `0 to avoid exception error if $h is empty
        $h+=($_-replace'(.)(?=\1)')*($offset+1) # accumulate a double message char or a single substring without inner doubles: arried -> arived, anna -> ana, etc
    }
}
$h*!($i-$message.Length)                        # repeat 0 or 1 times to return '' if the carrier does not contain the message characters in the right order

}

@(
    ,('hi'         ,'has it arrived?'    ,'hhas iit arived?', 'hhas it ariived?')
    ,('hi?'        ,'has it arrived?'    ,'hhas iit arived??', 'hhas it ariived??')
    ,('sir'        ,'has it arrived?'    ,'hass iit arrived?')
    ,('foo'        ,'has it arrived?'    ,'')
    ,('Car'        ,'Cats are cool.'     ,'CCaats arre col.')
    ,('car'        ,'Cats are cool.'     ,'')
    ,('Couch'      ,'Couch'              ,'CCoouucchh')
    ,('oo'         ,'oooooooooo'         ,'oooo')
    ,('o o'        ,'oooo oooa'          ,'oo  ooa')
    ,('er'         ,'error'              ,'eerorr', 'eerror')
    ,('a+b'        ,'anna+bob'           ,'aana++bbob')
) | % {
    $message,$carrier,$expected = $_
    $result = &$f $message $carrier
    "$($result-in$expected): $result"
}

Production:

True: hhas iit arived?
True: hhas iit arived??
True: hass iit arrived?
True:
True: CCaats arre col.
True:
True: CCoouucchh
True: oooo
True: oo  ooa
True: eerror
True: aana++bbob

0

C (gcc) , 69 + 12 = 81 octets

g(char*m,char*_){for(;*_;++_)*m-*_?_[-1]-*_&&p*_):p p*m++));*m&&0/0;}

Compiler avec (12 octets)

-Dp=putchar(

Essayez-le en ligne!

g(char*m,char*_){
    for(;*_;++_)        //step through _
        *m-*_?          //check if character should be encoded
            _[-1]-*_&&  //no? skip duplicates
                p*_)    //    print non-duplicates
        :p p*m++));     //print encoded character twice
    *m&&0/0;            //if m is not fully encoded, exit via Floating point exception
}
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.