Samuel Ribeiro Atv 1 - P2
Documentação da Atividade 01 - Matemática Discreta (P2)
Aluno: Samuel Ribeiro
https://onecompiler.org/python/44pnnh8s7
(LINK DE UM COMPILADOR ONLINE QUE PRESTA)
https://www.programiz.com/online-compiler/8AFN5jbUys2nB
Neste documento explico detalhadamente a lógica que utilizei para desenvolver a solução da lista de exercícios de Matemática Discreta. O código foi feito em Python e pensado para ser executado de forma estruturada, amigável e sem falhas na plataforma OneCompiler.
DISCLAIMER
Professora, como o OneCompiler é uma plataforma online, ele funciona de um jeito um pouquinho diferente do terminal normal do computador. No computador, o programa pausa e fica esperando a gente digitar cada valor (um por um) ao vivo.
Já no OneCompiler, ele não tem essa interação 'ao vivo'. Ele usa uma caixa de texto chamada STDIN (Standard Input). A gente precisa colocar todas as respostas que o programa vai pedir de uma vez só dentro dessa caixa antes de apertar o botão 'Run'.
O programa então vai 'engolir' essa caixa de texto de cima para baixo: a primeira linha do STDIN ele usa no primeiro input() (que é a escolha do menu), a segunda linha ele usa no próximo input(), e assim por diante.
Se a gente não preencher o STDIN com todas as respostas, o programa chega num ponto em que ele pede um número, mas a caixa de texto já acabou. No Python normal, isso daria um erro feio chamado EOFError (End Of File) e o programa iria 'quebrar' a execução. Mas para garantir que a minha solução fosse robusta, eu coloquei um tratamento com try/except EOFError em todas as entradas. Então, se o STDIN acabar no meio do caminho, meu código simplesmente percebe, encerra a operação graciosamente e "não quebra a aplicação" retornando ao menu principal.
OPÇÃO 1: TESTE DO EXERCÍCIO 1 (Conjuntos)
(Cria o Conjunto A = {1, 2, 3, 4}, o Conjunto B = {3, 4, 5, 6} e encerra)
1
1, 2, 3, 4
3, 4, 5, 6
0
OPÇÃO 2: TESTE DO EXERCÍCIO 2 (MDC, MMC, DIV e MOD)
(Calcula os valores para os números 12 e 18 e encerra)
2
12
18
0
OPÇÃO 3: TESTE DO EXERCÍCIO 3 (Aritmética Modular e Zn)
(Usa n=6, a=6, b=2, x=4 e encerra)
3
6
6
2
4
0
OPÇÃO 4: TESTE COMPLETO (Roda todos os 3 exercícios em sequência)
(Executa as operações dos 3 exercícios de uma vez e encerra com sucesso)
1
1, 2, 3, 4, 5
4, 5, 6, 7, 8
2
48
180
3
5
7
2
3
0
Na minha opinião fiz um excelente trabalho com os tratamentos e dividindo o código por funções seguindo a metodologia de coding que já uso no mercado de trabalho! Peço encarecidamente que tenha misericórdia desse código nessa avaliação <3
Função obter_inteiro
Criei essa função auxiliar no início do código para proteger todas as entradas de número inteiro do programa.
Percebi que se eu usasse apenas int(input()) diretamente, o programa quebraria com um erro fatal chamado ValueError toda vez que alguém digitasse uma letra, um espaço ou apertasse Enter sem digitar nada. Para evitar isso, criei essa função que tenta converter a entrada para número inteiro usando try/except. Se der errado, ela avisa que a entrada é inválida e pede de novo. Isso acontece dentro de um while True, ou seja, o programa fica em loop pedindo até receber um número válido de verdade.
Exercício 1: Operações e Propriedades de Conjuntos
Leitura dos conjuntos A e B
Optei por ler os elementos como um único texto, pedindo para o usuário separar por vírgula. Achei mais prático do que perguntar elemento por elemento com um loop interativo.
Depois, para ficar a prova de balas, substituo todas as vírgulas por espaços vazios usando replace(',', ' ') e logo em seguida aplico um split() sem parâmetros. O split() corta a string considerando qualquer sequência de espaços, resolvendo automaticamente o problema caso o usuário digite "1 2 3" ao invés de "1, 2, 3". A condição elem not in A garante que não haverá elementos repetidos, respeitando a definição matemática de conjunto.
Cálculo da União (A U B)
Copiei todos os elementos de A de uma vez com list(A) e depois varri o conjunto B. Para cada elemento de B, só adiciono na união se ele ainda não estiver lá. Isso garante que a lista final não tenha repetições.
Cálculo da Interseção (A ∩ B)
Percorri o conjunto A elemento por elemento. Se aquele elemento também existir dentro do conjunto B, então ele é comum aos dois e pertence à interseção. Fui adicionando cada um desses na lista intersecao.
Cálculo das Diferenças (A-B) e (B-A)
Para a diferença A menos B, percorri A e só guardei os elementos que não estão em B. Para a diferença B menos A, fiz o mesmo raciocínio de forma invertida, percorrendo B e guardando o que não está em A.
Produto Cartesiano (A x B)
O produto cartesiano exige combinar cada elemento de A com todos os de B. Para isso usei dois laços for aninhados: um percorre A e o interno percorre B. A cada passagem formo um par ordenado (a, b) e guardo na lista produto_cartesiano.
Verificação de Subconjunto
Para verificar se A está contido em B, criei uma variável a_contido_b começando como True. Percorri A e, se achar qualquer elemento que não esteja em B, mudo para False e dou break para parar a busca imediatamente, poupando processamento desnecessário. Fiz o mesmo para verificar se B está contido em A.
Cardinalidade
Usei a função len() para contar o número de elementos de cada conjunto e resultado das operações. A cardinalidade é simplesmente o tamanho da lista.
Exercício 2: MDC, MMC, DIV e MOD
Leitura dos números e validação
Usei a função obter_inteiro que criei no início para garantir que só números inteiros sejam aceitos. Depois coloquei uma trava: se qualquer um dos dois números for menor ou igual a zero, o programa avisa e encerra a função com return. Fiz isso por dois motivos: matematicamente o MDC é definido para inteiros positivos, e computacionalmente evito um ZeroDivisionError que quebraria o programa.
Divisão inteira (DIV) e Resto (MOD)
Em Python, o operador // já faz a divisão inteira diretamente, retornando o quociente sem casas decimais. O operador % retorna o resto da divisão. São operadores nativos da linguagem, sem precisar de nenhuma função especial.
MDC pelo Algoritmo de Euclides
Implementei o Algoritmo de Euclides manualmente usando um while. A lógica é: enquanto o segundo número não for zero, calculo o resto da divisão do primeiro pelo segundo. Depois, o primeiro vira o segundo e o segundo vira esse resto. Quando o segundo chegar a zero, o MDC é o valor que sobrou no primeiro. Imprimi cada passo para mostrar o raciocínio.
MMC a partir do MDC
Usei a propriedade matemática que diz que o produto de dois números é igual ao produto do MDC pelo MMC deles. Isolando o MMC, a fórmula fica: MMC = (num1 * num2) / MDC. Usei o operador // para manter como inteiro, pois essa divisão sempre é exata.
Exercício 3: Aritmética Modular, Congruência e Inverso em Zn
Criando o conjunto Zn
Usei list(range(n)) para criar o conjunto. O range(n) já gera os números de 0 até n-1 automaticamente, que é exatamente a definição de Zn = {0, 1, ..., n-1}.
Tabelas de Adição e Multiplicação Modular
Para montar as tabelas, usei dois laços for aninhados: o externo percorre as linhas (i) e o interno percorre as colunas (j). Para adição calculei (i + j) % n e para multiplicação calculei (i * j) % n. O módulo % n garante que o resultado sempre fique dentro do conjunto Zn. Usei f-strings com :2 para forçar cada número a ocupar dois caracteres, deixando a tabela alinhada visualmente.
Verificação de Congruência
Calculei a % n e b % n separadamente. Dois números são congruentes módulo n quando deixam o mesmo resto ao serem divididos por n. Então basta comparar se mod_a == mod_b.
Inverso Multiplicativo (Desafio Extra)
O inverso multiplicativo de x em Zn é um número y tal que (x * y) mod n = 1. Para encontrar, fiz uma busca percorrendo todos os elementos de Zn. Para cada y, calculei (x * y) % n. O primeiro que der resultado 1 é o inverso, guardo ele e saio do loop com break. Se varrer o Zn inteiro sem encontrar, o elemento não possui inverso.
Função main e Menu
Criei a função main com um while True para manter o menu ativo. O usuário escolhe qual exercício rodar digitando 1, 2 ou 3, ou digita 0 para encerrar. Se digitar qualquer outra coisa, o programa avisa que a opção é inválida e repete o menu.