Pièces de puzzle Matrix

10

(Inspiré au hasard par https://codegolf.meta.stackexchange.com/a/17272/42963 )

Étant donné une matrice rectangulaire de chiffres (c.-à-d. 0 - 9), Sortez les "morceaux" de la matrice comme si les chiffres étaient reliés entre eux pour former une seule pièce, dans l'ordre croissant par les chiffres. Les pièces sont garanties de se connecter uniquement orthongonalement - aucune pièce ne se connectera en diagonale. Il n'y aura jamais qu'un maximum de 10 pièces (c'est-à-dire qu'une 3pièce n'apparaîtra pas deux fois dans la même matrice).

Par exemple, étant donné la matrice

0 1 1 1
0 0 1 2
3 3 2 2

voici les pièces et un exemple de sortie:

0
0 0

1 1 1
  1

  2
2 2

3 3

L'espacement est important pour conserver la forme des pièces, mais les pièces n'ont pas nécessairement besoin d'espacement intérieur. Les pièces elles-mêmes devraient en quelque sorte être rendues distinctes de manière cohérente (par exemple, une nouvelle ligne entre les pièces, en s'assurant que chacune est un caractère différent, etc.). En outre, les espaces blancs superflus (par exemple, les retours à la ligne de fin ou les colonnes de début) ne sont pas autorisés. Par exemple, les éléments suivants seraient également valides:

0
00
111
 1
 2
22
33

ou

#
##

###
 #

 #
##

##

Mais ce ne serait pas le cas (notez les espaces derrière les 0s):

0      
0 0    

Les rotations ou réflexions ne sont pas non plus autorisées. Par exemple, la sortie

 1
111

pour la matrice ci-dessus est également invalide.

Les pièces de la matrice peuvent avoir des trous ou être un seul élément:

0 0 0 1
0 2 0 1
0 0 0 3

Ou, la pièce peut être la matrice entière:

0 0 0
0 0 0

Voici un cas de test plus grand et plus compliqué:

1 1 1 1 1 2 2
3 4 4 4 2 2 2
5 5 4 4 2 0 0
5 6 6 6 6 7 7
5 6 8 8 6 6 7
9 6 6 6 7 7 7

Et un exemple de sortie:

00

11111

 22
222
2

3

444
 44

55
5
5

6666
6  66
666

 77
  7
777

88

9

Règles et E / S

  • L'entrée et la sortie peuvent être fournies par n'importe quelle méthode pratique .
  • Vous pouvez l'imprimer sur STDOUT ou le renvoyer en tant que résultat de fonction.
  • Un programme complet ou une fonction sont acceptables.
  • Un espace de tête pour conserver la forme (par exemple, la forme en "T" de 1dans l'exemple) est requis, un espace cohérent pour rendre les pièces distinctes, et une seule nouvelle ligne de fin à la fin n'est autorisée, mais aucun autre espace n'est autorisé.
  • Vous pouvez supposer en toute sécurité que les pièces sont numérotées 0de manière Ncontiguë, ce qui signifie que (par exemple) 3ne serait pas ignoré dans une matrice à six pièces.
  • Les failles standard sont interdites.
  • Il s'agit de donc toutes les règles de golf habituelles s'appliquent et le code le plus court (en octets) l'emporte.
AdmBorkBork
la source
La sortie peut-elle réellement être une liste des pièces? Ou les E / S ne se font pas avec des chaînes mais avec des matrices et des entiers (avec -1ou un espace représentant un espace vide, ou absence d'élément si possible)?
Erik the Outgolfer le
Est-il acceptable si l'entrée est basée sur 1 (ne contient pas de zéros) et que la sortie utilise 0comme valeur de remplissage? Ainsi, chaque morceau serait sorti avec le reste des valeurs dans la matrice définie sur0
Luis Mendo
Indépendamment de ma question précédente: aucun autre espace n'est autorisé : pas même des espaces de fin pour que toutes les lignes soient de longueur égale?
Luis Mendo
@EriktheOutgolfer L'absence d'un élément serait OK, car cela ne produit que la "pièce" elle-même. La sortie d'une matrice entière pour chaque pièce avec -1ou une autre valeur au lieu de rien / espace ne serait cependant pas OK.
AdmBorkBork
@AdmBorkBork Oh, alors l'espace ( ' ') devrait-il être utilisé dans ce cas?
Erik the Outgolfer le

Réponses:

2

05AB1E , 20 19 octets

ZƒNQ2Fζʒà}}ε0Ü}0ð:,

-1 octet grâce à @ Mr.Xcoder .

Affiche des listes 2D de pièces (avec 1et espaces " ") par nouvelle ligne.

Essayez-le en ligne ou vérifiez tous les cas de test ou imprimez tous les cas de test .

Explication:

Z              # Get the maximum digit of the (implicit) matrix-input (implicitly flattens)
 ƒ             # Loop in the range [0, max]:
  NQ           #  Check for each digit in the (implicit) matrix if it's equal to the index
    2F    }    #  Inner loop two times:
      ζ        #   Zip/transpose; swapping rows/columns
       ʒ }     #   Filter the inner lists by:
        à      #    Get the max of the list
               #  (so all rows/columns containing only 0s are removed)
  ε  }         #  Map the remaining rows:
   0Ü          #   Remove all trailing 0s
  0ð:          #  Then replace any remaining 0 with a space " "
     ,         #  And output the piece-matrix with a trailing newline
Kevin Cruijssen
la source
2

Haskell, 133 132 129 octets

f x=[until(any(>"!"))(tail<$>)m|m<-[[until((>'!').last)init r|r<-[[last$' ':[s|s==n]|s<-z]|z<-x],any(>'!')r]|n<-['0'..'9']],m>[]]

Prend la matrice comme une liste de chaînes et renvoie une liste de liste de chaînes.

Essayez-le en ligne!

                                    -- example matrix: ["0111","0012","3322"] 
                                    --
[          |n<-[0..9]]              -- for each digit 'n' from '0' .. '9'
  [  |z<-x]                         --   for each line 'z' of the input matrix 'x'
   [      |s<-z]                    --     for each digit 's' of line 'z'
      last$' ':[s|s==n]             --       take 's' if 's'=='n', else a space
                                    --       now we have a list of 10 matrices where
                                    --       each matrix contains only the
                                    --       corresponding digit 'n' at it's original
                                    --       position and spaces for all other digits
                                    --       -> [["0   ","00  ","    "],[" 111","  1 ","    "],["    ","   2","  22"],["    ","    ","33  "],["    ","    ","    "],["    ","    ","    "],["    ","    ","    "],["    ","    ","    "],["    ","    ","    "],["    ","    ","    "]]
   [     |r<-[    ],any(>'!')r]     --     loop through rows 'r' and keep those with
                                    --     at least one non-space element
    until((>'!').last)init r        --     and remove trailing spaces
                                    --     -> [["0","00"],[" 111","  1"],["   2","  22"],["33"],[],[],[],[],[],[]]
   [     |m<-[   ],m>[]]            --   loop through matrices 'm' and keep only
                                    --   non-empty
    until(any(>"!"))(tail<$>)m      --   and remove common leading spaces
                                    --   -> [["0","00"],["111"," 1"],[" 2","22"],["33"]]
nimi
la source
2

Gelée , 18 octets

ẎQṢ=€ẸƇZ$⁺œr€ɗ€0o⁶

Essayez-le en ligne!

Renvoie une liste de pièces, où 1représente une partie d'une pièce et ' 'est un remplissage. Les ' 's de fin sont supprimés.

Erik le Outgolfer
la source
ẎQ=€devrait faire, bien que nous ayons besoin des pièces dans l'ordre croissant, donc 9Ż=€(sauf si nous ne devons pas inclure les "pièces inexistantes" dans ce cas ẎQṢ=€)
Jonathan Allan
@JonathanAllan Correction du problème, bien que je ne sois pas certain que 9Ż=€cela ne fonctionnera pas (je pense que "les espaces étrangers [...] ne sont pas autorisés" s'étend également aux tableaux, c'est pourquoi je coupe).
Erik the Outgolfer le
Ouais, ça a du sens.
Jonathan Allan
2

Python 3 , 271 209 206 183 176 172 172 191 octets

lambda t:[[[*"".join(' #'[i==d]for i in r).rstrip()]for r in[w[min(r.index(d)for r in t if d in r):max(len(R)-R[::-1].index(d)for R in t if d in R)]for w in t if d in w]]for d in{*sum(t,[])}]

Essayez-le en ligne!

Edit: Un peu de nettoyage et -5 grâce à @ Jonathan Frech .

Edit: -3 -26 encore une fois grâce à @ Jonathan Frech .

Edit: -7 encore grâce à @ Jonathan Frech .

Edit: +19: Comme indiqué par @ nimi, la sortie précédente avait un format incorrect.


L'entrée est une matrice sous forme de liste de listes:

Input =  [[0, 1, 1, 1],
          [0, 0, 1, 2],
          [3, 3, 2, 2]]

La sortie est une liste de matricies:

Output = [[['#'],
           ['#', '#']],
          [['#', '#', '#'],
           [' ', '#']],
          [[' ', '#'],
           ['#', '#']],
          [['#', '#']]],

Non golfé:

O = ' '
X = '#'

def digits(t):
    return {d for r in t for d in r}

def rows_with_digit(table, digit):
    return [row for row in table if digit in row]

def table_with_digit(table, digit):
    subtable = rows_with_digit(table, digit)
    left_most_column = min([row.index(digit) for row in subtable])
    right_most_column = max([len(row) - row[::-1].index(digit) for row in subtable])
    return [row[left_most_column:right_most_column] for row in subtable]

def format_table(table, digit):
    return [[X if i==digit else O for i in row] for row in table]

def f(table):
    D = digits(table)
    R = []
    for d in D:
        digit_table = table_with_digit(table, d)
        R.append(format_table(digit_table, d))    
    return R
Nishioka
la source
1
176 octets .
Jonathan Frech du
2

Python 2 , 173 172 165 165 octets

s=input()
for i in sorted(set(sum(s,[]))):R=[''.join([' ',i][c==i]for c in r)for r in s if i in r];print'\n'.join(t[min(r.find(i)for r in R):t.rfind(i)+1]for t in R)

Essayez-le en ligne!

-15 octets à partir d'une observation de nimi .

Sous forme de programme, prend en entrée une liste de listes de caractères uniques; sorties en imprimant les pièces trouvées en utilisant leur caractère.

Chas Brown
la source
@AdmBorkBork - D'accord, j'ai raté ce critère. Fixé maintenant.
Chas Brown
2

C # (.NET Core) , 258 , 238 octets

Sans LINQ.

EDIT: Incarnation Of Ignorance indiquant de meilleures déclarations var! Ty ty.

p=>{int j=0,o=0,l=0,x=p.GetLength(1),d=p.Length;while(j<d){int t=j/x,u=j++%x,z=p[t,u];o=z>o?z:o;l=z<l?z:l;}var s="";for(var m=l;m<=o;m++){j=0;while(j<d){int t=j/x,u=j++%x;s+=(p[t,u]==m?p[t,u]+"":" ")+(u==x-1?"\n":"");}s+="\n";}return s;};

Essayez-le en ligne!

Destroigo
la source
1
238 octets
Incarnation de l'ignorance
1

Python 2 , 291 octets

import re
t=input()
a,b=t.split(),{c for c in t if' '<c}
for c in sorted((b,a)[int(max(a))==len(a)],key=int):s=re.sub(r'[^%s\s]'%c,' ',t).split('\n');print"\n".join(''.join(l[i]for i in sorted({i for l in s for i,j in enumerate(l)if j in c})if i<len(l)).rstrip()for l in s if l.strip())+'\n'

Essayez-le en ligne!

Attend une piqûre délimitée par des guillemets en entrée. Un pourcentage semi-ridicule du code est dédié à la gestion des entrées non séparées par des espaces / non remplies par des espaces.

Explication sans golf:

# built-in python regex handling.
import re
# get argument from STDIN
t=input()
# get elements which are whitespace separated, and all distinct non-whitespace characters
a,b=set(t.split()),{c for c in t if' '<c}
                # choose whichever set has the appropriate number of values based on its max element
                # for non-space separated inputs, this prevents values like '333' for 4-piece sets
                (b,a)[int(max(a))==len(a)]
# get elements in order by their integer value
# this will force the items to print in order, since sets are unordered
for c in sorted(..........................,key=int):
      # using regex substitute, replace any instance that DOESN'T match the current value or a whitespace with a space
      re.sub(r'[^%s\s]'%c,' ',t)
    # split replaced string into lines on line breaks
    s=...........................split('\n')
                # for each line in replaced input
                for l in s
                           # get the index and value of each item in line
                           for i,j in enumerate(l)
             # get distinct indexes which have a value that appears in the current piece
             {i ..................................if j in c}
    # get ordered list of distinct indexes
    a=sorted(...............................................)
                                                               # for each line in the replaced input
                                                               # only return values where line has non-whitespace values
                                                               for l in s if l.strip()
                           # get the value for each index that has a non-space value on other lines
                           # as long as that index exists (for non-space-padded inputs)
                           # this ensures that the spaces between values, if any, are removed
                           # there may still be trailing spaces
                           l[i]for i in a if i<len(l)
                   # join characters back into one string, and remove trailing whitespace
                   ''.join(..........................).rstrip()
    # join the lines back together with line breaks, and terminate with an extra line break
    # print output to screen
    print"\n".join(...................................................................)+'\n'
Triggernométrie
la source
Vous êtes autorisé à spécifier le format d'entrée (par exemple, comme une liste de listes, ou comme un paragraphe séparé par des espaces) si cela rend votre code plus golfeur.
AdmBorkBork
1

Rétine , 75 octets

$
¶9
.-10{T`9d`d`.$
*;(s`(\d)(?!.*\1$)
 
 +¶
¶
G`\d
/^\d|^$/m^+m`^.

.$
$&¶

Essayez-le en ligne! Explication:

$
¶9

Ajoutez un chiffre à l'entrée. Cela représente le compteur de boucle. La nouvelle ligne simplifie la suppression des espaces de fin.

.-10{

Inhibez la sortie par défaut et répétez exactement 10 fois.

T`9d`d`.$

Avancez le chiffre de la boucle.

*;(

Générez le résultat du reste du script, puis restaurez le tampon.

s`(\d)(?!.*\1$)
 

Remplacez tous les chiffres qui ne correspondent pas au chiffre de la boucle par des espaces. (Parce que cela utilise une anticipation et qu'il n'y a rien à prévoir à ce stade, cela remplace également le chiffre de la boucle.)

 +¶
¶

Supprimez tous les espaces de fin.

G`\d

Supprimez toutes les lignes vides.

/^\d|^$/m^+

Répétez l'opération tant qu'aucune ligne ne commence par un chiffre ...

m`^.

... supprimez le premier caractère de chaque ligne.

.$
$&¶

S'il reste quelque chose, ajoutez une nouvelle ligne pour séparer chaque forme de la suivante. (Ceci est fait pour éviter les sauts de ligne parasites pour les chiffres manquants.)

Neil
la source
Il est garanti qu'il n'y aura jamais de "chiffre manquant" si cela raccourcit votre code.
AdmBorkBork
@AdmBorkBork Je ne pense pas que cela aiderait. Ce qui serait le plus susceptible d'aider, c'est de ne pas avoir à sortir les pièces dans l'ordre numérique. Est-ce permis?
Neil
Non, c'est la moitié du défi, sinon ce serait trop facile. ;-)
AdmBorkBork
1

Fusain , 43 octets

WS⊞υιFχ«≔Φυ№κIιθ¿θ«UTFθ«Fκ«¿⁼λIιλ→»M±Lκ¹»D⎚

Essayez-le en ligne! Le lien est vers la version détaillée du code. Explication:

WS⊞υι

Lisez l'entrée dans un tableau. (Cela pourrait être supprimé si j'utilisais un format d'entrée moche.)

Fχ«

Boucle sur les 10 chiffres.

≔Φυ№κIιθ

Obtenez les lignes qui contiennent ces chiffres.

¿θ«

Vérifiez que le chiffre a bien été trouvé (pour éviter la sortie de nouvelles lignes parasites).

UT

Désactivez le rembourrage automatique.

Fθ«

Faites une boucle sur les lignes trouvées.

Fκ«

Boucle sur chaque colonne ...

¿⁼λIιλ→»

... si le caractère d'entrée actuel est égal au chiffre de la boucle actuelle, imprimez-le sinon déplacez le curseur vers la droite.

M±Lκ¹»

Passez au début de la ligne suivante. L'utilisation de commandes de mouvement comme celle-ci permet au charbon de bois de couper la sortie des deux côtés.

D⎚

Vider et effacer la toile prête pour le chiffre suivant. Cela permet aux différents chiffres d'avoir différentes quantités de rognage.

J'ai essayé une approche programmatique, mais qui pesait 47 octets, même si elle aurait également été de 43 octets pendant une brève période lorsqu'elle a été Equalsvectorisée:

UTWS⊞υιFχ«≔ΦEυEκ⁼μIιΣκθEθ⭆✂κ⌊Eθ⌕μ¹⁻Lκ⌕⮌κ¹¦¹⎇μι 

Essayez-le en ligne! Le lien est vers la version détaillée du code. Explication:

UT

Désactivez le rembourrage automatique.

WS⊞υι

Lisez l'entrée dans un tableau.

Fχ«

Boucle sur les 10 chiffres.

≔ΦEυEκ⁼μIιΣκθ

Comparez chaque caractère avec l'entrée et créez un tableau booléen, puis filtrez les lignes sans correspondance.

Eθ⭆✂κ⌊Eθ⌕μ¹⁻Lκ⌕⮌κ¹¦¹⎇μι 

Faites une boucle sur les lignes restantes et coupez de la première correspondance de n'importe quelle ligne à la dernière correspondance de la ligne actuelle, puis mappez le tableau booléen sur des chiffres ou des espaces, qui sont ensuite imprimés implicitement sous la forme d'un tableau de chaînes.

Neil
la source
1

Langue Wolfram 101 octets

Il doit y avoir un moyen beaucoup plus efficace d'accomplir cela.

(g=#;Column[Table[Grid@Map[Replace[#,Thread[Complement[u=Union@Flatten@g,{n}]->""]]&/@#&,g],{n,u}]])&
DavidC
la source
1

Perl 5, 97 octets

$x=$_;for$i(0..9){$_=$x;y/ //d;s/(?!$i)./ /g;s/ *$//gm;s/^
//gm;s/^ //gm until/^(?! )/m;$\.=$_}}{

TIO

Explication

-p0777                       # options to read whole intput and print special var by default

$x=$_;                       # save default var (input) into $x
for$i(0..9){                 # for $i in 0..9
    $_=$x;                   #   restore default var 
    y/ //d;                  #   remove all space char
    s/(?!$i)./ /g;           #   replace all char except $i by a space
    s/ *$//gm;               #   remove trailing space
    s/^\n//gm;               #   remove empty lines
    s/^ //gm until/^(?! )/m; #   remove leading space until there is no more
    $\.=$_                   #   append default var to output record separator
}
}{                           # trick with -p to output only reacord separator
Nahuel Fouilleul
la source
1

APL (Dyalog Unicode) , 38 octets SBCS

Fonction de préfixe tacite anonyme. Prend une matrice numérique comme argument et renvoie une liste de chaînes de listes. Chaque liste de chaînes représente une pièce avec des 1s séparés par des espaces . Les espaces de début et internes (mais pas de fin) sont des espaces.

⊂{' +$'R''↓⍕' '@~{⍉⍵⌿⍨∨/⍵}⍣2⊢⍺=⍵}¨∪∘,

Essayez-le en ligne!

∪∘, les éléments uniques de la matrice de ravel (aplatie)

⊂{ Pour chacun de ceux as , appelez la fonction suivante avec la matrice entière as :

⍺=⍵ indiquer où se trouve le numéro de cette pièce dans la matrice

 rendement qui (se sépare 2de )

{}⍣2 Appliquer deux fois la fonction suivante ( est la matrice booléenne):

  ∨/ masque pour les rangées avec au moins un 1(allumé. réduction des rangées OU)

  ⍵⌿⍨ utiliser cela pour filtrer les lignes

   transposer (donc nous le faisons aussi sur les colonnes, puis transposer en arrière)

' '@~ remplacer par des espaces aux endroits où pas (c'est-à-dire où 0)

 format comme matrice de caractères

 divisé en liste de chaînes

' +$'⎕R'' PCRE remplace les espaces de fin (n'importe quel nombre d'espaces suivis d'une fin de ligne) par rien

Adam
la source
1

Japt , 29 octets

AÆ®®¥X ÑÃÃÕfx Õfx ®¬r0S x1
fl

Essayez-le en ligne!

Mis à jour pour se conformer à un formatage de sortie plus strict.

Sorties sous forme de liste de pièces, chaque pièce étant représentée par une liste de lignes, en utilisant 2 comme caractère de remplissage.

Explication:

AÆ                            #For the numbers 0-9:
  ®®    ÃÃ                    # Map over each digit in the input:
    ¥X                        #  True if it equals the current number, false otherwise
       Ñ                      #  Multiply by 2 to turn the bool into a number
          Õfx                 # Remove columns that are all 0
              Õfx             # Remove rows that are all 0
                  ®           # For each remaining row:
                   ¬          #  Turn it into a string
                    r0S       #  Replace "0" with " "
                        x1    #  Trim spaces from the right
fl                            #Remove unused pieces
Kamil Drakari
la source
Vous avez oublié de supprimer tous les éléments falsede fin des listes internes. Voici un pastebin pour que je puisse mieux expliquer ce qui est censé être la sortie. N'hésitez pas à demander à OP de clarifier, mais d'après ce que je comprends du défi, tous les espaces blancs à la fin ne devraient pas du tout être présents dans la sortie.
Kevin Cruijssen
0

Python 3 , 133 octets

lambda s:[dedent(re.sub(" *$","",re.sub(f"[^{c}\\n]"," ",s),0,8)).strip("\n")for c in sorted(*s)[1:]]
from textwrap import*
import re

Essayez-le en ligne!

Prend une chaîne séparée par une nouvelle ligne, retourne une liste de chaînes séparées par une nouvelle ligne. Utilise textwrap.dedentpour se débarrasser des espaces principaux.

Chouette noire Kai
la source
@AdmBorkBork Ignoré cette règle, corrigé
Black Owl Kai
0

Gelée , 19 octets

ŒĠµŒṬZSƇ$⁺ị⁾# œr€⁶)

Essayez-le en ligne!

Un lien monadique prenant la matrice en entrée et renvoyant une liste d'une liste irrégulière par pièce. Le pied de page affiche cela joliment, mais je pense que la sortie sans cela est conforme aux règles de la question.

Nick Kennedy
la source