Puis-je vivre ici?

16

Dans le jeu Terraria , l'une des mécaniques de jeu consiste à construire des maisons pour qu'un PNJ puisse y emménager. Il existe un ensemble de règles strictes pour ce qui compte comme maison valide ou non. Voici la liste des règles:

  1. La superficie totale de la maison doit être d'au moins 60 carreaux carrés, mais inférieure à 750. De plus, la taille de la maison, y compris le cadre extérieur, doit être au moins l'une de celles-ci:

    5x12
    6x10
    7x9
    8x8
    9x7
    10x6
    12x5
    15x4
    

    par souci de simplicité, vous pouvez supposer en toute sécurité que: a) Toutes les maisons d'entrée seront des rectangles, et b) aucune tuile solide #ne sera à l'intérieur de la maison. Voici notre cadre 12x6 (dessiné en magnifique ASCII):

    ############
    #          #
    #          #
    #          #
    #          #
    ############
    
  2. La maison doit être recouverte de murs d'arrière-plan. Ce ne sont pas des tuiles solides, mais plutôt un mur derrière la maison dans la troisième dimension. Les trous sont autorisés, mais aucun trou ne peut être plus grand que 4x4. S'il y a une ligne ou une colonne de 5 caractères d'espace ou plus dans une ligne, c'est un trou plus grand que 4x4 et la maison n'est pas valide. Plusieurs trous sont également autorisés, mais il doit y avoir au moins un seul mur.

    ############
    #**********#
    #**********#
    #**********#
    #**********#
    ############
    
    ############
    #*    *    #
    #*    *    #
    #*    *    #
    #******    #
    ############  (Still acceptable since neither hole is larger than 4x4 and there is a separator)
    
    ############
    #    ******#
    #***    ***#
    #    ******#
    #***    ***#
    ############  (Also still valid. No row or column of blank spaces is longer or taller than 4.)
    
  3. Il doit y avoir une entrée. Cela peut être une porte |sur les côtés ou une plate-forme -au sol ou au plafond. Si la seule entrée se trouve dans un coin, le PNJ ne peut pas entrer. De plus, si vous avez une plate-forme comme sol, vous devez avoir au moins un seul bloc solide pour que le PNJ puisse se tenir debout. Ce bloc solide ne peut pas être directement adjacent aux parois latérales à gauche ou à droite. Ce sont toutes des maisons valides avec entrées:

    ############
    #**********#
    |**********#
    #**********#
    #**********|
    ############  (Multiple doors, or doors up high are okay)
    
    ############
    #**********#
    #**********#
    #**********#
    #**********#
    #######----#
    
    #----#######
    #**********#
    #**********#
    #**********#
    #**********#
    ############
    
  4. Il doit y avoir au moins une source lumineuse $, une table Tet une chaise C, bien que plus soit autorisé. La source de lumière peut être dans l'air ou au sol, mais la table et la chaise doivent toutes deux être au sol, par exemple sur la rangée la plus basse.

    ############
    #**********#
    #**********#
    #***$******|
    #****TC****|
    ############
    

    En outre, vous pouvez supposer qu'il y a un mur derrière un meuble, de sorte qu'une torche, une chaise ou une table peuvent compter comme séparateur entre deux trous.

    ############
    #*    *    #
    #*    *    #
    #*    $    #
    #**TC******|
    ############
    

Le défi

Vous devez écrire la fonction la plus courte qui prend une maison sous forme de chaîne ASCII et renvoie vrai / faux, qu'il s'agisse ou non d'un logement valide. Vous pouvez prendre cela comme une chaîne délimitée par des sauts de ligne, une liste de chaînes ou tout autre moyen tant que cela est raisonnable. Pour moi, veuillez inclure un programme court afin que je puisse tester s'il fonctionne correctement ou non.

Pour référence, ce sont toutes des entrées invalides:

############
-**********#
-****$*****#
-**********#
-******TC**#
############  (You can't have platforms on the sidewalls)

###########-
#**********#
#**********#
#****$*****#
#**T***C***#
###########|  (NPC can't enter because the only entrances are on the corner)

############
#**********#
#******$***#
#**********#
#T****C****#
##--------##  (NPC has nowhere to stand)

############
#**********#
#**********#
#**********#
#**$**TC***#
##########|#  (Door cannot be in the floor or ceiling)

############
#**********#
#**********#
#**********#
|**   T C  #
############  (Since table and chair do not count as a background wall, the hole in background is too wide)

####### ####
#**********#
#**********#
#****$*****#
#**T***C***|
############  (There's a hole in the frame.)


###########################################################################
#                                                                         #
#                                                                         #
#                                                                         #
#                                                                         #
#                                                                         #
#                                                                         #
#                                                                         #
#                                                                         #
#                                                                         #
###########################################################################  (House is 75x11, which is too big.)

Classement

DJMcMayhem
la source
6
Un défi cool, mon amoureux de Terraria.
Rɪᴋᴇʀ
Peut-on supposer que les trous seront rectangulaires? Sinon, cela pourrait utiliser un cas de test où le tout ne rentre pas dans le 4x4 mais qui ne contient jamais plus de 4 espaces d'affilée.
Martin Ender
Il y a de nombreux points que je trouve flous. 1. Le cadre doit-il être rectangulaire? " toutes les maisons seront des rectangles " suggère qu'elles le font, mais n'exclut pas clairement les cadres qui ne sont pas rectangulaires mais qui vont dans les quatre coins de leur cadre de délimitation aligné sur l'axe. Et peut-être que des trous peuvent être entourés #. 2. Comme Martin l'a demandé, que signifie exactement " aucun trou ne peut être plus grand que 4x4 "? (Notez également que ce n'est qu'à ma troisième lecture que j'ai été certain de comprendre ce qu'était le trou. Vous devriez écrire la spécification pour les personnes qui n'ont pas joué au jeu).
Peter Taylor
1
3. " Ce bloc solide ne peut pas être directement adjacent aux murs " - qu'est-ce qu'un mur? À partir du point 2, cela semble être le cas *, mais cela exclurait les exemples donnés de portes valides. 4. Est-ce que " sur le terrain " signifie "dans l'avant-dernière rangée" ou "au-dessus de #"? 5. " Cela ne s'applique pas à la table et aux chaises. " Cela signifie-t-il donc qu'un trou 4x4 avec un Tou Cdirectement en dessous est trop grand? 6. "Le PNJ ne peut pas entrer parce que les seules entrées sont au coin " Je ne pense pas que la spécification ait dit quoi que ce soit sur les coins. Peuvent-ils l'être -ou |s'il y a d'autres portes?
Peter Taylor
7. Si les entrées dans un coin sont un problème parce qu'elles n'admettent pas l'accès, cela signifie-t-il que chacune *doit être accessible depuis une entrée? Ou sont isolés *au milieu des trous autorisés, des trous qui coupent toute la pièce en deux avec un seul côté ayant une entrée autorisée, et des entrées qui vont directement dans un trou autorisé?
Peter Taylor

Réponses:

2

Python 2, 503 439 octets

Pas super court, mais c'est une solution. Faites-moi savoir si vous voyez quelque chose au golf. Je recommanderais également de regarder ma version non golfée, car elle est en fait lisible.

Edit: Tous les if s en dehors d'une boucle ont été combinés en bas.

def f(s):
 s=s.split("\n");e=l=0;h=len(s);w=len(s[0])
 for c in s[0][1:-1]+s[-1][1:-1]:
    if(c in"#-")<1:return 0
    if"-"==c:e=1
 for r in s[1:-1]:
    if(r[0]in"#|")*(r[-1]in"#|")<1or" "*5in r:return 0
    if"$"in r:l=1
 for r in zip(*s):
    if" "*5in`r`[2::5]:return 0
 if(h*w<60)+(h*w>749)+(w<5)+(h<4)or" "in s[0][0]+s[0][-1]+s[-1][0]+s[-1][-1]or("T"in s[-2])*("C"in s[-2])*l<1or("#"in s[-1][2:-2])<1or"|"in"".join(s[1:-1])<1>e:return 0
 return 1

Essayez-le en ligne

Non golfé:

Affiche également la raison du résultat False, à des fins de débogage.

def f(s):

    # check dimensions
    s=s.split("\n")
    h=len(s)
    w=len(s[0])
    if h*w < 60 or h*w > 749 or w<5 or h<4: return False,"Size"

    # top / bottom
    e=0
    for c in s[0][1:-1]+s[-1][1:-1]:
        if(c in"#-")<1:return False,"T/B"

        # entrance
        if"-"==c:e=1

    # no spaces in corners -_-
    if" "in s[0][0]+s[0][-1]+s[-1][0]+s[-1][-1]: return False,"Corner"

    # light, table, chair
    l=t=c=0

    # left / right
    for r in s[1:-1]:
        if(r[0]in"#|")*(r[-1]in"#|")<1: return False,"L/R"

        # walls, put above
        if" "*5in r: return False,"Walls"

        # light
        if"$"in r:l=1

    # table, chair
    if"T"in s[-2]:t=1
    if"C"in s[-2]:c=1

    if l*t*c<1: return False,"L/T/C"

    # wall columns
    for r in zip(*s): # Transpose
        if" "*5in`r`[2::5]: # Tuple to string
            return False,"Walls"

    # entrance
    if"|"in"".join(s[1:-1])<1>e: return False,"Entrance"

    # place to stand
    if("#"in s[-1][2:-2])<1: return False,"Stand"

    return True

Version non golfée en ligne

mbomb007
la source