🤔 Para Refletir :
"Fazer um jogo é sempre muito mais difícil do que jogar um jogo..."
- Rafael_Sol_MAKER

DESAFIO: Código Maldito

DESAFIO: Código Maldito


mini-banner-codigo-maldito-png.6449

Na Torre do Desespero, na fronteira gelada do Condado Braveheart, vive um Cientista Louco, imerso em seus cálculos e experimentos ele vive preso em devaneios de sua mente criando enigmas infinitos e largando-os no caminho a sua solitária torre, aguardando alguém que possa solucionar seus problemas...



Um grupo de crianças encontrou uma caixa com diversos brinquedos para se divertirem no Halloween. Nessa caixa eles encontraram:​
  • Aranhas de plástico​
  • Sapos de borracha​
  • Dentaduras​
  • Fantasminhas que brilham no escuro​
  • Bruxinhas​
JC, Hellen, Franklin, Daniel e Samuel gostaram da caixa e decidiram distribuir os brinquedos de acordo com seus gostos. Mas como Samuel é um menino que gosta criar brincadeira com qualquer coisa com seus amigos e resolveu propor um pequeno jogo para eles. Mas antes disso, Samuel resolveu colocar seus amigos em uma fila de frente à caixa, na seguinte ordem:​
  • Samuel​
  • Franklin​
  • Hellen​
  • JC​
  • Daniel​
Feito isso, Samuel sempre retirará um brinquedo da caixa e o brinquedo será passado para as crianças de mão em mão, respeitando a ordem da fila até uma delas pegar o brinquedo que ela gosta. Se a criança receber um brinquedo que ela gosta, pegará para ela e guardará em sua mochila. Se o brinquedo é aquele que a criança não gosta, passa para a próxima que está atrás.
Abaixo, temos informações importantes para descobrir qual brinquedo cada criança gosta.​
  1. Hellen gosta de Fantasminhas que brilham no escuro.​
  2. Daniel nunca vai receber Bruxinhas.​
  3. Franklin não gosta de Bruxinhas.​
  4. As outras crianças nunca receberão Sapos de borracha.​
  5. As Dentaduras sempre serão passadas para todas as crianças.​
Desenvolva um código que faz a distribuição dos brinquedos para cada criança. A linguagem ficará à sua escolha, no entanto você deverá escolher 1 (um) paradigma ou 3 (três):​
  • Imperativa Estruturada​
  • Imperativa Orientada a Objetos​
  • Declarativa Funcional​
Se o participante escolher 2 (dois) paradigmas, será considerado somente o primeiro paradigma escolhido seguindo a ordem da lista acima.


É preferível que o participante envie a solução através de um repositório Git (pode ser qualquer plataforma que usa Git: Github, Gitlab, Bitbucket, etc.). Se não tiver como enviar como repositório, pode enviar todo o código aqui como resposta a este tópico, mas precisa especificar a estrutura dos arquivos separadamente e os códigos de cada um deles, se for necessário.
Recomendamos que coloque a solução dentro do spoiler para que os outros participantes acabem não vendo sem querer e/ou ser influenciado pela resposta do outro participante.
Não será considerado como aprovado qualquer outra forma de padronização de envio. Em caso de quaisquer dúvidas, não hesite em usar o espaço deste tópico para poder saná-las o quanto antes.


Use o modelo abaixo se não for enviar via Github.
Estrutura:
Código:
App/
    Person.php
index.php

App/Person.php
Php:
<?php

namespace App;

class Person
{
    public function __construct(
        private string $name,
        private int $age
    )
    {}


    public function __get(string $key)
    {
        if (property_exists($this, $key))
            return $this->$key;
        return null;
    }


    public function __set(string $key, $value)
    {
        if (property_exists($this, $key))
            $this->$key = $value;
    }
}

index.php
Php:
<?php

use App\Person;

/** @var Person */
$person = new Person('Jubileu', 21);
echo 'Nome: ' . $person->name;
echo 'Idade: ' . $person->age;



A resolução do código será testada em um ambiente de testes unitários para validação da solução. Se o problema for resolvido em um dos paradigmas selecionados e passar por todos os testes, o participante receberá 100 Bravecoins.
O participante também pode tentar escolher os 3 paradigmas. Cada código vai um bônus de 50 Bravecoins para cada teste aprovado. Se os 3 códigos passarem nos testes, ainda terão um bônus de 50 Bravecoins por desenvolver a mesma solução em 3 paradigmas diferentes.


Escolheu um paradigma e passou no teste+100 Bravecoins
Escolheu os 3 paradigmas e, pelo menos, um dos testes passou+100 Bravecoins +50/teste aprovado
Escolheu os 3 paradigmas e os todos eles passaram no teste+100 Bravecoins +150 Bravecoins + 50 Bravecoins

Notícias recentes:

Top Screens #339
FL por FL
0 0
Top Screens
Top Screens #338
FL por FL
0 2
Top Screens
Top Screens #337
FL por FL
3 6
Top Screens
Top Screens #336
FL por FL
1 2
Top Screens
#CondaDev : Mostre seu amor a Phil Alone!
ドーベルマン por ドーベルマン
9 8
Eventos

Comentários recentes:

Dr.XGB

Dr.XGB

Administração
Administração
Muito bem, pessoal!
O evento CÓDIGO MALDITO encerrou-se.
Muito Obrigado a todos que participaram!

Abaixo, vou disponibilizar o repositório com as soluções do desafio.

Também podemos conferir o desenvolvimento das soluções que fiz ao vivo no meu canal:
(foi dividido em duas partes porque a live caiu, como de praxe ._.)

Nos vemos no próximo evento!
Dr.XGB

Dr.XGB

Administração
Administração
É, realmente o negócio é meio pesado x)
Duro que ele compila uma pancada de coisa da Mathlib, que tem toda uma bagagem enorme de teoria. Se abrir os logs de compilação dele tem 3k+ arquivos ali, e a maioria é relativamente grandinho kk

Instalar essas coisas no Windows de fato é uma missão impossível. Se tiver um instaladorzinho, estilo Python e Node, até vai; no mais, o jeito é usar o WSL haha



Mais ou menos, meu ponto era mais que o enunciado não exige, necessariamente, uma relação um-pra-um entre os gostos crianças e os tipos de brinquedos (que foi o que eu assumi ali, pra provar os gostos de cada criança); teoricamente poderia ter mais de um brinquedo de cada tipo na caixa, é só que o programa meio que ignora e finge que tem só um (porque de fato eu não tratei isso, tinha entendido que era um de cada mesmo).

Pra ilustrar, fiz um programinha em Prolog aqui que respeita todas as informações dadas, mas permite cada criança gostar de mais de um brinquedo (e mais de uma criança gostar do mesmo), ou de nenhum:
Código:
%--------------------------------------------------------------------------------------------------
% Definições.
%--------------------------------------------------------------------------------------------------

% Crianças
child(samuel).
child(franklin).
child(hellen).
child(jc).
child(daniel).

% Brinquedos.
toy(aranha).
toy(sapo).
toy(dentadura).
toy(fantasma).
toy(bruxinha).
toy('outro brinquedo').

% Fila
queue([samuel, franklin, hellen, jc, daniel]).
prev(Child, PrevChild) :- queue(Q), nextto(PrevChild, Child, Q).
next(Child, NextChild) :- prev(NextChild, Child).

%--------------------------------------------------------------------------------------------------
% Recebe/não recebe.
%--------------------------------------------------------------------------------------------------

% 5. As Dentaduras sempre serão passadas para todas as crianças.
receives(_, dentadura).

% Uma criança recebe um brinquedo se é a primeira da fila, ou se a criança anterior na fila recebe
% o brinquedo e não gosta dele.
receives(Child, Toy) :-
    child(Child), toy(Toy),
    (
        prev(Child, PrevChild) -> (
            receives(PrevChild, Toy),
            dislikes(PrevChild, Toy)
        );
        true
    ).

% 2. Daniel nunca vai receber Bruxinhas.
never_receives(daniel, bruxinha).

% 4. As outras crianças nunca receberão Sapos de borracha.
never_receives(Child, sapo) :-
    child(Child),
    Child \= samuel.

%--------------------------------------------------------------------------------------------------
% Gosta/não gosta/pode gostar.
%--------------------------------------------------------------------------------------------------

% 1. Hellen gosta de Fantasminhas que brilham no escuro.
likes(hellen, fantasma).

% Se a criança recebe o brinquedo e a próxima nunca recebe, então a criança gosta do brinquedo.
likes(Child, Toy) :-
    receives(Child, Toy),
    next(Child, NextChild),
    never_receives(NextChild, Toy).

% 3. Franklin não gosta de Bruxinhas.
dislikes(franklin, bruxinha).

% Uma criança pode gostar do brinquedo se ela não desgostar do brinquedo, e se nenhuma criança
% depois dela na fila precisa receber o brinquedo.
might_like(Child, Toy) :-
    child(Child), toy(Toy),
    \+ dislikes(Child, Toy),
    queue(Q), nth0(I, Q, Child),
    forall((nth0(J, Q, OtherChild), J > I), \+ receives(OtherChild, Toy)).

%--------------------------------------------------------------------------------------------------
% Simulação da brincadeira.
%--------------------------------------------------------------------------------------------------

take(Child, Toy, Final) :-
    write(Child), write(" pegou "), writeln(Toy),
    Final = Child.

pass(Child, Toy, Final) :-
    next(Child, NextChild) *-> (
        write(Child), write(" passou "), write(Toy), write(" para "), writeln(NextChild),
        pass_around(NextChild, Toy, Final)
    );
    write("ninguém pegou "), writeln(Toy),
    Final = ninguém.

pass_around(Child, Toy, Final) :-
    % Se a criança gosta do brinquedo, ela fica com ele.
    likes(Child, Toy) -> take(Child, Toy, Final);
    % Se ela pode ou não gostar do brinquedo, simula os dois casos.
    might_like(Child, Toy) -> (
        take(Child, Toy, Final);
        pass(Child, Toy, Final)
    );
    % Se ela não gosta do brinquedo, passa pro próximo.
    pass(Child, Toy, Final).

play(Toy, Final) :- pass_around(samuel, Toy, Final).

:- initialization(main).
main :-
    forall(toy(Toy), (
        write("["), write(Toy), writeln("]"),
        forall(play(Toy, Final), (
            write(Toy), write(" fica com "), writeln(Final), nl)))).

Com esse programa aí dá pra ver que tem ambiguidade nos gostos das crianças; em particular:
Código:
?- forall(might_like(C, T), (write(C), write(" pode gostar de "), writeln(T))).
samuel pode gostar de aranha
samuel pode gostar de sapo
samuel pode gostar de fantasma
samuel pode gostar de bruxinha
samuel pode gostar de outro brinquedo
franklin pode gostar de aranha
franklin pode gostar de sapo
franklin pode gostar de fantasma
franklin pode gostar de outro brinquedo
hellen pode gostar de aranha
hellen pode gostar de sapo
hellen pode gostar de fantasma
hellen pode gostar de bruxinha
hellen pode gostar de outro brinquedo
jc pode gostar de aranha
jc pode gostar de sapo
jc pode gostar de fantasma
jc pode gostar de bruxinha
jc pode gostar de outro brinquedo
daniel pode gostar de aranha
daniel pode gostar de sapo
daniel pode gostar de dentadura
daniel pode gostar de fantasma
daniel pode gostar de bruxinha
daniel pode gostar de outro brinquedo
true.

A query mostra todos os brinquedos que cada criança pode gostar. Claro, tem alguns brinquedos que algumas crianças tem que gostar:
Código:
?- forall(likes(C, T), (write(C), write(" deve gostar de "), writeln(T))).
hellen deve gostar de fantasma
samuel deve gostar de sapo
true.

E alguns que elas não podem gostar:
Código:
?- forall((child(C), toy(T), \+ might_like(C, T)), (write(C), write(" não pode gostar de "), writeln(T))).
samuel não pode gostar de dentadura
franklin não pode gostar de dentadura
franklin não pode gostar de bruxinha
hellen não pode gostar de dentadura
jc não pode gostar de dentadura
true.

Mas fora esses casos, as crianças podem não gostar de nenhum brinquedo, gostar de vários, etc..

Se puder assumir a correspondência um-pra-um, i.e. que dá pra inferir os brinquedos do Franklin, JC e Daniel por eliminação, então esse código aqui completa o predicado likes, ajusta o dislikes, e valida as condições de coerência pra tudo, e aí a saída é equivalente à do programa em Lean:
Código:
    % Descobre os gostos do franklin, jc e daniel.
    forall(member(C, [franklin, jc, daniel]),
        (
            might_like(C, T),
            \+ likes(_, T), T \= 'outro brinquedo',
            asserta(likes(C, T))
        )
    ),

    forall(child(C), (asserta(dislikes(C, T) :- \+ likes(C, T)))),

    % Valida coerência dos gostos.
    \+ (likes(C, T), \+ might_like(C, T)),
    \+ (likes(C1, T), likes(C2, T), C1 \= C2),
    \+ (likes(C, T1), likes(C, T2), T1 \= T2),

    % Valida coerência da condição de receber ou não um brinquedo.
    \+ (receives(C, T), never_receives(C, T))

De toda forma, esse programinha aí dá todas as possibilidades válidas de atribuição de brinquedo por criança, acho que tá valendo (e fica aí a solução implementada mais um paradigma de programação, hehe).

EDIT: Usei SWI-Prolog, tem o https://swish.swi-prolog.org/ que roda online se não quiser instalar (embora provavelmente seja mais tranquilo que Lean hehe), é meio lentinho mas funciona (exceto o asserta, infelizmente) hehe
Chique!
Você recebeu +200 Bravecoins como gratificação por refatorar a solução. Já está na conta. :cool:
Brandt

Brandt

Colaboração
Colaboração
Custei um pouco pra entender que o lake demora alguns minutos pra cada compilação porque ele só mostra o feedback na primeira compilação. A partir da segunda fica só o cursor piscando sem avisar nada. Então pensei que o bicho tinha bugado de vez e acabei reinstalando o lake diversas vezes achando que era problema dele mesmo. Mas depois descobri que a solução era botar pra rodar, tomar um copo d'água, correr 500m e tomar um banho que o programa terminava de rodar kkkkkkk !!
Isso pq eu rodei no Linux, pq se fosse no Windows estava instalando até hoje pq, provavelmente, eles pediriam para eu encontrar um Sapo violeta chinês no mar vermelho do Havaí cantando "Acordando o prédio" na voz do Luan Santana pra conseguir instalar. No Linux é só rodar o cURL e ser feliz.
É, realmente o negócio é meio pesado x)
Duro que ele compila uma pancada de coisa da Mathlib, que tem toda uma bagagem enorme de teoria. Se abrir os logs de compilação dele tem 3k+ arquivos ali, e a maioria é relativamente grandinho kk

Instalar essas coisas no Windows de fato é uma missão impossível. Se tiver um instaladorzinho, estilo Python e Node, até vai; no mais, o jeito é usar o WSL haha

Parece que o sistema estava fortemente acoplado para que a criança recebesse somente um brinquedo (isso vc até justificou no tópico)

Mais ou menos, meu ponto era mais que o enunciado não exige, necessariamente, uma relação um-pra-um entre os gostos crianças e os tipos de brinquedos (que foi o que eu assumi ali, pra provar os gostos de cada criança); teoricamente poderia ter mais de um brinquedo de cada tipo na caixa, é só que o programa meio que ignora e finge que tem só um (porque de fato eu não tratei isso, tinha entendido que era um de cada mesmo).

Pra ilustrar, fiz um programinha em Prolog aqui que respeita todas as informações dadas, mas permite cada criança gostar de mais de um brinquedo (e mais de uma criança gostar do mesmo), ou de nenhum:
Código:
%--------------------------------------------------------------------------------------------------
% Definições.
%--------------------------------------------------------------------------------------------------

% Crianças
child(samuel).
child(franklin).
child(hellen).
child(jc).
child(daniel).

% Brinquedos.
toy(aranha).
toy(sapo).
toy(dentadura).
toy(fantasma).
toy(bruxinha).
toy('outro brinquedo').

% Fila
queue([samuel, franklin, hellen, jc, daniel]).
prev(Child, PrevChild) :- queue(Q), nextto(PrevChild, Child, Q).
next(Child, NextChild) :- prev(NextChild, Child).

%--------------------------------------------------------------------------------------------------
% Recebe/não recebe.
%--------------------------------------------------------------------------------------------------

% 5. As Dentaduras sempre serão passadas para todas as crianças.
receives(_, dentadura).

% Uma criança recebe um brinquedo se é a primeira da fila, ou se a criança anterior na fila recebe
% o brinquedo e não gosta dele.
receives(Child, Toy) :-
    child(Child), toy(Toy),
    (
        prev(Child, PrevChild) -> (
            receives(PrevChild, Toy),
            dislikes(PrevChild, Toy)
        );
        true
    ).

% 2. Daniel nunca vai receber Bruxinhas.
never_receives(daniel, bruxinha).

% 4. As outras crianças nunca receberão Sapos de borracha.
never_receives(Child, sapo) :-
    child(Child),
    Child \= samuel.

%--------------------------------------------------------------------------------------------------
% Gosta/não gosta/pode gostar.
%--------------------------------------------------------------------------------------------------

% 1. Hellen gosta de Fantasminhas que brilham no escuro.
likes(hellen, fantasma).

% Se a criança recebe o brinquedo e a próxima nunca recebe, então a criança gosta do brinquedo.
likes(Child, Toy) :-
    receives(Child, Toy),
    next(Child, NextChild),
    never_receives(NextChild, Toy).

% 3. Franklin não gosta de Bruxinhas.
dislikes(franklin, bruxinha).

% Uma criança pode gostar do brinquedo se ela não desgostar do brinquedo, e se nenhuma criança
% depois dela na fila precisa receber o brinquedo.
might_like(Child, Toy) :-
    child(Child), toy(Toy),
    \+ dislikes(Child, Toy),
    queue(Q), nth0(I, Q, Child),
    forall((nth0(J, Q, OtherChild), J > I), \+ receives(OtherChild, Toy)).

%--------------------------------------------------------------------------------------------------
% Simulação da brincadeira.
%--------------------------------------------------------------------------------------------------

take(Child, Toy, Final) :-
    write(Child), write(" pegou "), writeln(Toy),
    Final = Child.

pass(Child, Toy, Final) :-
    next(Child, NextChild) *-> (
        write(Child), write(" passou "), write(Toy), write(" para "), writeln(NextChild),
        pass_around(NextChild, Toy, Final)
    );
    write("ninguém pegou "), writeln(Toy),
    Final = ninguém.

pass_around(Child, Toy, Final) :-
    % Se a criança gosta do brinquedo, ela fica com ele.
    likes(Child, Toy) -> take(Child, Toy, Final);
    % Se ela pode ou não gostar do brinquedo, simula os dois casos.
    might_like(Child, Toy) -> (
        take(Child, Toy, Final);
        pass(Child, Toy, Final)
    );
    % Se ela não gosta do brinquedo, passa pro próximo.
    pass(Child, Toy, Final).

play(Toy, Final) :- pass_around(samuel, Toy, Final).

:- initialization(main).
main :-
    forall(toy(Toy), (
        write("["), write(Toy), writeln("]"),
        forall(play(Toy, Final), (
            write(Toy), write(" fica com "), writeln(Final), nl)))).

Com esse programa aí dá pra ver que tem ambiguidade nos gostos das crianças; em particular:
Código:
?- forall(might_like(C, T), (write(C), write(" pode gostar de "), writeln(T))).
samuel pode gostar de aranha
samuel pode gostar de sapo
samuel pode gostar de fantasma
samuel pode gostar de bruxinha
samuel pode gostar de outro brinquedo
franklin pode gostar de aranha
franklin pode gostar de sapo
franklin pode gostar de fantasma
franklin pode gostar de outro brinquedo
hellen pode gostar de aranha
hellen pode gostar de sapo
hellen pode gostar de fantasma
hellen pode gostar de bruxinha
hellen pode gostar de outro brinquedo
jc pode gostar de aranha
jc pode gostar de sapo
jc pode gostar de fantasma
jc pode gostar de bruxinha
jc pode gostar de outro brinquedo
daniel pode gostar de aranha
daniel pode gostar de sapo
daniel pode gostar de dentadura
daniel pode gostar de fantasma
daniel pode gostar de bruxinha
daniel pode gostar de outro brinquedo
true.

A query mostra todos os brinquedos que cada criança pode gostar. Claro, tem alguns brinquedos que algumas crianças tem que gostar:
Código:
?- forall(likes(C, T), (write(C), write(" deve gostar de "), writeln(T))).
hellen deve gostar de fantasma
samuel deve gostar de sapo
true.

E alguns que elas não podem gostar:
Código:
?- forall((child(C), toy(T), \+ might_like(C, T)), (write(C), write(" não pode gostar de "), writeln(T))).
samuel não pode gostar de dentadura
franklin não pode gostar de dentadura
franklin não pode gostar de bruxinha
hellen não pode gostar de dentadura
jc não pode gostar de dentadura
true.

Mas fora esses casos, as crianças podem não gostar de nenhum brinquedo, gostar de vários, etc..

Se puder assumir a correspondência um-pra-um, i.e. que dá pra inferir os brinquedos do Franklin, JC e Daniel por eliminação, então esse código aqui completa o predicado likes, ajusta o dislikes, e valida as condições de coerência pra tudo, e aí a saída é equivalente à do programa em Lean:
Código:
    % Descobre os gostos do franklin, jc e daniel.
    forall(member(C, [franklin, jc, daniel]),
        (
            might_like(C, T),
            \+ likes(_, T), T \= 'outro brinquedo',
            asserta(likes(C, T))
        )
    ),

    forall(child(C), (asserta(dislikes(C, T) :- \+ likes(C, T)))),

    % Valida coerência dos gostos.
    \+ (likes(C, T), \+ might_like(C, T)),
    \+ (likes(C1, T), likes(C2, T), C1 \= C2),
    \+ (likes(C, T1), likes(C, T2), T1 \= T2),

    % Valida coerência da condição de receber ou não um brinquedo.
    \+ (receives(C, T), never_receives(C, T))

De toda forma, esse programinha aí dá todas as possibilidades válidas de atribuição de brinquedo por criança, acho que tá valendo (e fica aí a solução implementada mais um paradigma de programação, hehe).

EDIT: Usei SWI-Prolog, tem o https://swish.swi-prolog.org/ que roda online se não quiser instalar (embora provavelmente seja mais tranquilo que Lean hehe), é meio lentinho mas funciona (exceto o asserta, infelizmente) hehe
  • Curtir
Reações: Dr.XGB
Canal_JPÃO

Canal_JPÃO

Membro
Membro
Vc bateu na trave, meu nobre! Só trocou de uma criança :LOL:
troca o do franklin e do daniel entao k
  • Curtir
Reações: Dr.XGB
Dr.XGB

Dr.XGB

Administração
Administração
Eu achei bem bacana, mas como não sei programar eu vou pela logica kk, só pra participar mesmo S2.

Samuel: Sapos de boracha Hellen: fantasminhas JC: BRUXINHAS DANIEL: ARANHA FRANKLIN: DENTADURA
Vc bateu na trave, meu nobre! Só trocou de uma criança :LOL:
  • Kekeke
Reações: Canal_JPÃO

Deixe seu comentário:

Você deve fazer login ou se registrar para responder aqui.
Voltar
Topo Inferior