Repository: DesignLiquido/delegua
Pull request #627 (2024-02-06 21:37:32)

Tuplas
Implementa https://github.com/DesignLiquido/delegua/discussions/617


Patch:
diff --git a/fontes/analisador-semantico/analisador-semantico.ts b/fontes/analisador-semantico/analisador-semantico.ts
index 3318d042..29f699e9 100644
--- a/fontes/analisador-semantico/analisador-semantico.ts
+++ b/fontes/analisador-semantico/analisador-semantico.ts
@@ -1,4 +1,4 @@
-import { Agrupamento, Atribuir, Binario, Chamada, Construto, ExpressaoRegular, FimPara, FormatacaoEscrita, FuncaoConstruto, Literal, Logico, Super, TipoDe, Variavel, Vetor } from '../construtos';
+import { Agrupamento, Atribuir, Binario, Chamada, Construto, ExpressaoRegular, FimPara, FormatacaoEscrita, FuncaoConstruto, Literal, Logico, Super, TipoDe, Tupla, Variavel, Vetor } from '../construtos';
 import {
     Aleatorio,
     Bloco,
@@ -60,6 +60,9 @@ export class AnalisadorSemantico implements AnalisadorSemanticoInterface {
         this.atual = 0;
         this.diagnosticos = [];
     }
+    visitarExpressaoTupla(expressao: Tupla): Promise<any> {
+        return Promise.resolve();
+    }
 
     visitarDeclaracaoAleatorio(declaracao: Aleatorio): Promise<any> {
         return Promise.resolve();
diff --git a/fontes/analisador-semantico/dialetos/analisador-semantico-birl.ts b/fontes/analisador-semantico/dialetos/analisador-semantico-birl.ts
index 081d3293..14b24d52 100644
--- a/fontes/analisador-semantico/dialetos/analisador-semantico-birl.ts
+++ b/fontes/analisador-semantico/dialetos/analisador-semantico-birl.ts
@@ -1,4 +1,4 @@
-import { Atribuir, ExpressaoRegular, FimPara, FormatacaoEscrita, Literal, Super, TipoDe, Variavel } from '../../construtos';
+import { Atribuir, ExpressaoRegular, FimPara, FormatacaoEscrita, Literal, Super, TipoDe, Tupla, Variavel } from '../../construtos';
 import {
     Aleatorio,
     Bloco,
@@ -61,6 +61,9 @@ export class AnalisadorSemanticoBirl implements AnalisadorSemanticoInterface {
         this.atual = 0;
         this.diagnosticos = [];
     }
+    visitarExpressaoTupla(expressao: Tupla): Promise<any> {
+        return Promise.resolve();
+    }
     visitarExpressaoAcessoElementoMatriz(expressao: any) {
         return Promise.resolve();
     }
diff --git a/fontes/analisador-semantico/dialetos/analisador-semantico-mapler.ts b/fontes/analisador-semantico/dialetos/analisador-semantico-mapler.ts
index b3e8d75f..23f9034c 100644
--- a/fontes/analisador-semantico/dialetos/analisador-semantico-mapler.ts
+++ b/fontes/analisador-semantico/dialetos/analisador-semantico-mapler.ts
@@ -1,4 +1,4 @@
-import { Atribuir, Binario, Chamada, Construto, ExpressaoRegular, FimPara, FormatacaoEscrita, Literal, Super, TipoDe, Vetor } from '../../construtos';
+import { Atribuir, Binario, Chamada, Construto, ExpressaoRegular, FimPara, FormatacaoEscrita, Literal, Super, TipoDe, Tupla, Vetor } from '../../construtos';
 import {
     Aleatorio,
     Bloco,
@@ -50,6 +50,9 @@ export class AnalisadorSemanticoMapler implements AnalisadorSemanticoInterface {
         this.atual = 0;
         this.diagnosticos = [];
     }
+    visitarExpressaoTupla(expressao: Tupla): Promise<any> {
+        return Promise.resolve();
+    }
     visitarExpressaoAcessoElementoMatriz(expressao: any) {
         return Promise.resolve();
     }
diff --git a/fontes/analisador-semantico/dialetos/analisador-semantico-visualg.ts b/fontes/analisador-semantico/dialetos/analisador-semantico-visualg.ts
index bbf7844b..288e87ab 100644
--- a/fontes/analisador-semantico/dialetos/analisador-semantico-visualg.ts
+++ b/fontes/analisador-semantico/dialetos/analisador-semantico-visualg.ts
@@ -1,4 +1,4 @@
-import { Atribuir, Chamada, ExpressaoRegular, FimPara, FormatacaoEscrita, FuncaoConstruto, Literal, Super, TipoDe, Variavel, Vetor } from "../../construtos";
+import { Atribuir, Chamada, ExpressaoRegular, FimPara, FormatacaoEscrita, FuncaoConstruto, Literal, Super, TipoDe, Tupla, Variavel, Vetor } from "../../construtos";
 import {
     Aleatorio,
     Bloco,
@@ -50,6 +50,9 @@ export class AnalisadorSemanticoVisuAlg implements AnalisadorSemanticoInterface
         this.atual = 0;
         this.diagnosticos = [];
     }
+    visitarExpressaoTupla(expressao: Tupla): Promise<any> {
+        return Promise.resolve();
+    }
 
     erro(simbolo: SimboloInterface, mensagem: string): void {
         this.diagnosticos.push({
diff --git a/fontes/construtos/index.ts b/fontes/construtos/index.ts
index d127c5f5..3a865b85 100644
--- a/fontes/construtos/index.ts
+++ b/fontes/construtos/index.ts
@@ -22,6 +22,7 @@ export * from './literal';
 export * from './logico';
 export * from './super';
 export * from './tipo-de';
+export * from './tuplas';
 export * from './unario';
 export * from './variavel';
 export * from './vetor';
diff --git a/fontes/construtos/tuplas/tupla.ts b/fontes/construtos/tuplas/tupla.ts
index 2933b783..7ef1a587 100644
--- a/fontes/construtos/tuplas/tupla.ts
+++ b/fontes/construtos/tuplas/tupla.ts
@@ -7,6 +7,6 @@ export abstract class Tupla implements Construto {
     valor?: any;
 
     async aceitar(visitante: VisitanteComumInterface): Promise<any> {
-        throw new Error('Método não implementado.');
+        return await visitante.visitarExpressaoTupla(this);
     }
 }
diff --git a/fontes/formatadores/formatador-delegua.ts b/fontes/formatadores/formatador-delegua.ts
index 29c5fee3..c6aa614c 100644
--- a/fontes/formatadores/formatador-delegua.ts
+++ b/fontes/formatadores/formatador-delegua.ts
@@ -18,6 +18,7 @@ import {
     Logico,
     Super,
     TipoDe,
+    Tupla,
     Unario,
     Variavel,
     Vetor,
@@ -76,6 +77,10 @@ export class FormatadorDelegua implements VisitanteComumInterface {
         this.deveIndentar = true;
     }
 
+    visitarExpressaoTupla(expressao: Tupla): any {
+        return "";
+    }
+
     visitarDeclaracaoClasse(declaracao: Classe) {
         this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}classe ${declaracao.simbolo.lexema} {${this.quebraLinha}`;
 
diff --git a/fontes/formatadores/formatador-portugol-studio.ts b/fontes/formatadores/formatador-portugol-studio.ts
index 49d7dae4..6f6f3b51 100644
--- a/fontes/formatadores/formatador-portugol-studio.ts
+++ b/fontes/formatadores/formatador-portugol-studio.ts
@@ -1,4 +1,4 @@
-import { AcessoIndiceVariavel, AcessoMetodoOuPropriedade, Agrupamento, AtribuicaoPorIndice, Atribuir, Binario, Chamada, Construto, DefinirValor, Dicionario, ExpressaoRegular, FimPara, FormatacaoEscrita, FuncaoConstruto, Isto, Literal, Logico, Super, TipoDe, Unario, Variavel, Vetor } from "../construtos";
+import { AcessoIndiceVariavel, AcessoMetodoOuPropriedade, Agrupamento, AtribuicaoPorIndice, Atribuir, Binario, Chamada, Construto, DefinirValor, Dicionario, ExpressaoRegular, FimPara, FormatacaoEscrita, FuncaoConstruto, Isto, Literal, Logico, Super, TipoDe, Tupla, Unario, Variavel, Vetor } from "../construtos";
 import { Classe, Const, ConstMultiplo, Expressao, FuncaoDeclaracao, Enquanto, Escolha, Escreva, Fazer, Importar, Para, ParaCada, Se, Tente, Var, VarMultiplo, Bloco, Continua, EscrevaMesmaLinha, Leia, LeiaMultiplo, Retorna, Sustar, Declaracao, Falhar, Aleatorio } from "../declaracoes";
 import { VisitanteComumInterface } from "../interfaces";
 import { ContinuarQuebra, RetornoQuebra, SustarQuebra } from "../quebras";
@@ -20,7 +20,9 @@ export class FormatadorPortugolStudio implements VisitanteComumInterface {
         this.devePularLinha = true;
         this.deveIndentar = true;
     }
-
+    visitarExpressaoTupla(expressao: Tupla): Promise<any> {
+        throw new Error("Método não implementado");
+    }
     visitarDeclaracaoClasse(declaracao: Classe) {
         throw new Error("Método não implementado");
     }
diff --git a/fontes/formatadores/formatador-visualg.ts b/fontes/formatadores/formatador-visualg.ts
index 5da369c5..222b8cf8 100644
--- a/fontes/formatadores/formatador-visualg.ts
+++ b/fontes/formatadores/formatador-visualg.ts
@@ -1,10 +1,61 @@
-import { AcessoIndiceVariavel, AcessoMetodoOuPropriedade, Agrupamento, AtribuicaoPorIndice, Atribuir, Binario, Chamada, Construto, DefinirValor, Dicionario, ExpressaoRegular, FimPara, FormatacaoEscrita, FuncaoConstruto, Isto, Literal, Logico, Super, TipoDe, Unario, Variavel, Vetor } from "../construtos";
-import { Aleatorio, Classe, Const, ConstMultiplo, Expressao, FuncaoDeclaracao, Enquanto, Escolha, Escreva, Fazer, Importar, Para, ParaCada, Se, Tente, Var, VarMultiplo, Bloco, Continua, EscrevaMesmaLinha, Leia, LeiaMultiplo, Retorna, Sustar, Declaracao, Falhar } from "../declaracoes";
-import { SimboloInterface, VisitanteComumInterface } from "../interfaces";
-import { ContinuarQuebra, RetornoQuebra, SustarQuebra } from "../quebras";
-import tiposDeSimbolos from "../tipos-de-simbolos/visualg";
-
-export class FormatadorVisualG implements VisitanteComumInterface {
+import {
+    AcessoIndiceVariavel,
+    AcessoMetodoOuPropriedade,
+    Agrupamento,
+    AtribuicaoPorIndice,
+    Atribuir,
+    Binario,
+    Chamada,
+    Construto,
+    DefinirValor,
+    Dicionario,
+    ExpressaoRegular,
+    FimPara,
+    FormatacaoEscrita,
+    FuncaoConstruto,
+    Isto,
+    Literal,
+    Logico,
+    Super,
+    TipoDe,
+    Tupla,
+    Unario,
+    Variavel,
+    Vetor,
+} from '../construtos';
+import {
+    Aleatorio,
+    Classe,
+    Const,
+    ConstMultiplo,
+    Expressao,
+    FuncaoDeclaracao,
+    Enquanto,
+    Escolha,
+    Escreva,
+    Fazer,
+    Importar,
+    Para,
+    ParaCada,
+    Se,
+    Tente,
+    Var,
+    VarMultiplo,
+    Bloco,
+    Continua,
+    EscrevaMesmaLinha,
+    Leia,
+    LeiaMultiplo,
+    Retorna,
+    Sustar,
+    Declaracao,
+    Falhar,
+} from '../declaracoes';
+import { SimboloInterface, VisitanteComumInterface } from '../interfaces';
+import { ContinuarQuebra, RetornoQuebra, SustarQuebra } from '../quebras';
+import tiposDeSimbolos from '../tipos-de-simbolos/visualg';
+
+export class FormatadorVisuAlg implements VisitanteComumInterface {
     indentacaoAtual: number;
     quebraLinha: string;
     tamanhoIndentacao: number;
@@ -20,32 +71,31 @@ export class FormatadorVisualG implements VisitanteComumInterface {
         this.tamanhoIndentacao = tamanhoIndentacao;
 
         this.indentacaoAtual = 0;
-        this.codigoFormatado = "";
+        this.codigoFormatado = '';
         this.devePularLinha = false;
         this.deveIndentar = true;
-        this.contadorDeclaracaoVar = 0
+        this.contadorDeclaracaoVar = 0;
         this.deveAdicionarInicio = true;
-        this.retornoFuncaoAtual = undefined
+        this.retornoFuncaoAtual = undefined;
     }
 
     visitarDeclaracaoAleatorio(declaracao: Aleatorio): any {
-        this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}aleatorio `
-        if ((declaracao.argumentos.max > 0) && (declaracao.argumentos.min > 0)) {
-            this.codigoFormatado += `${declaracao.argumentos.min}, ${declaracao.argumentos.max}${this.quebraLinha}`
+        this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}aleatorio `;
+        if (declaracao.argumentos.max > 0 && declaracao.argumentos.min > 0) {
+            this.codigoFormatado += `${declaracao.argumentos.min}, ${declaracao.argumentos.max}${this.quebraLinha}`;
         } else {
-            this.codigoFormatado += `ON${this.quebraLinha}`
+            this.codigoFormatado += `ON${this.quebraLinha}`;
         }
-        this.formatarDeclaracaoOuConstruto(declaracao.corpo)
-
+        this.formatarDeclaracaoOuConstruto(declaracao.corpo);
     }
     visitarDeclaracaoClasse(declaracao: Classe) {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarDeclaracaoConst(declaracao: Const): any {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarDeclaracaoConstMultiplo(declaracao: ConstMultiplo): any {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarExpressaoDeAtribuicao(expressao: Atribuir) {
         this.codigoFormatado += `${expressao.simbolo.lexema} <- `;
@@ -56,99 +106,102 @@ export class FormatadorVisualG implements VisitanteComumInterface {
         }
     }
     visitarDeclaracaoDeExpressao(declaracao: Expressao) {
-        this.codigoFormatado += " ".repeat(this.indentacaoAtual);
+        this.codigoFormatado += ' '.repeat(this.indentacaoAtual);
         this.formatarDeclaracaoOuConstruto(declaracao.expressao);
     }
     visitarDeclaracaoDefinicaoFuncao(declaracao: FuncaoDeclaracao) {
         this.retornoFuncaoAtual = declaracao.tipoRetorno;
         this.contadorDeclaracaoVar = 2;
-        this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}funcao `;
+        this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}funcao `;
         if (declaracao.simbolo) {
             this.codigoFormatado += `${declaracao.simbolo.lexema}`;
         }
 
-
-        let primeiraOcorrenciaVar = declaracao.funcao.corpo.findIndex(item => item instanceof Var);
-        var ultimaOcorrenciaIndex = declaracao.funcao.corpo.slice().reverse().findIndex(item => item instanceof Var);
-        var ultimaOcorrenciaPosicao = ultimaOcorrenciaIndex >= 0 ? declaracao.funcao.corpo.length - 1 - ultimaOcorrenciaIndex : -1;
+        let primeiraOcorrenciaVar = declaracao.funcao.corpo.findIndex((item) => item instanceof Var);
+        var ultimaOcorrenciaIndex = declaracao.funcao.corpo
+            .slice()
+            .reverse()
+            .findIndex((item) => item instanceof Var);
+        var ultimaOcorrenciaPosicao =
+            ultimaOcorrenciaIndex >= 0 ? declaracao.funcao.corpo.length - 1 - ultimaOcorrenciaIndex : -1;
 
         let indiceParaRemover = [];
         if (primeiraOcorrenciaVar > -1 && ultimaOcorrenciaPosicao > -1) {
             this.codigoFormatado += this.quebraLinha;
             for (let i = primeiraOcorrenciaVar; i <= ultimaOcorrenciaPosicao; i++) {
                 this.formatarDeclaracaoOuConstruto(declaracao.funcao.corpo[i]);
-                indiceParaRemover.push(i)
+                indiceParaRemover.push(i);
             }
         }
 
         for (let posicao of indiceParaRemover) {
-            declaracao.funcao.corpo.splice(posicao, 1)
+            declaracao.funcao.corpo.splice(posicao, 1);
         }
-        this.codigoFormatado += this.quebraLinha
-        this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}inicio${this.quebraLinha}`
+        this.codigoFormatado += this.quebraLinha;
+        this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}inicio${this.quebraLinha}`;
 
         this.formatarDeclaracaoOuConstruto(declaracao.funcao);
-        this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}fimfuncao${this.quebraLinha}`;
+        this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}fimfuncao${this.quebraLinha}`;
     }
     visitarDeclaracaoEnquanto(declaracao: Enquanto) {
-        this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}enquanto(`;
+        this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}enquanto(`;
         this.formatarDeclaracaoOuConstruto(declaracao.condicao);
         this.codigoFormatado += ` ) faca`;
         this.codigoFormatado += this.quebraLinha;
 
         this.formatarDeclaracaoOuConstruto(declaracao.corpo);
-        this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}fimenquanto`;
+        this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}fimenquanto`;
     }
     visitarDeclaracaoEscolha(declaracao: Escolha) {
-        this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}escolha (`;
+        this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}escolha (`;
         this.formatarDeclaracaoOuConstruto(declaracao.identificadorOuLiteral);
 
         this.codigoFormatado += `)${this.quebraLinha}`;
         this.indentacaoAtual += this.tamanhoIndentacao;
         for (let caminho of declaracao.caminhos) {
-            this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}caso `;
+            this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}caso `;
             for (let condicao of caminho.condicoes) {
-                this.formatarDeclaracaoOuConstruto(condicao)
-                this.codigoFormatado += ", "
+                this.formatarDeclaracaoOuConstruto(condicao);
+                this.codigoFormatado += ', ';
             }
             if (caminho.condicoes.length > 0) {
                 this.codigoFormatado = this.codigoFormatado.slice(0, -2);
             }
             this.codigoFormatado += this.quebraLinha;
-            this.formatarBlocoOuVetorDeclaracoes(caminho.declaracoes)
+            this.formatarBlocoOuVetorDeclaracoes(caminho.declaracoes);
         }
 
         if (declaracao.caminhoPadrao.declaracoes.length > 0) {
-            this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}outrocaso`;
+            this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}outrocaso`;
             this.codigoFormatado += this.quebraLinha;
-            this.formatarBlocoOuVetorDeclaracoes(declaracao.caminhoPadrao.declaracoes)
+            this.formatarBlocoOuVetorDeclaracoes(declaracao.caminhoPadrao.declaracoes);
         }
 
         this.indentacaoAtual -= this.tamanhoIndentacao;
-        this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}fimescolha${this.quebraLinha}`;
+        this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}fimescolha${this.quebraLinha}`;
     }
     visitarDeclaracaoEscreva(declaracao: Escreva) {
-        this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}escreva(`;
+        this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}escreva(`;
         for (let argumento of declaracao.argumentos) {
             this.formatarDeclaracaoOuConstruto(argumento);
-            this.codigoFormatado += ", ";
+            this.codigoFormatado += ', ';
         }
-        if (declaracao.argumentos.length && this.codigoFormatado[this.codigoFormatado.length - 2] === ",") {
+        if (declaracao.argumentos.length && this.codigoFormatado[this.codigoFormatado.length - 2] === ',') {
             this.codigoFormatado = this.codigoFormatado.slice(0, -2);
         }
         this.codigoFormatado += `)${this.quebraLinha}`;
     }
     visitarDeclaracaoFazer(declaracao: Fazer) {
-        this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}repita${this.quebraLinha}`
+        this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}repita${this.quebraLinha}`;
         this.formatarDeclaracaoOuConstruto(declaracao.caminhoFazer);
-        this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}ate `
-        this.formatarDeclaracaoOuConstruto(declaracao.condicaoEnquanto)
+        this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}ate `;
+        this.formatarDeclaracaoOuConstruto(declaracao.condicaoEnquanto);
     }
     visitarDeclaracaoImportar(declaracao: Importar) {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarDeclaracaoPara(declaracao: Para): any {
-        this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}para `;
+        this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}para `;
         this.devePularLinha = false;
         if (declaracao.inicializador) {
             if (Array.isArray(declaracao.inicializador)) {
@@ -162,24 +215,21 @@ export class FormatadorVisualG implements VisitanteComumInterface {
             }
         }
 
-        if (declaracao.condicao instanceof Binario)
-            this.codigoFormatado += ` ate ${declaracao.condicao.direita.valor}`;
-        else
-            this.formatarDeclaracaoOuConstruto(declaracao.condicao);
-
+        if (declaracao.condicao instanceof Binario) this.codigoFormatado += ` ate ${declaracao.condicao.direita.valor}`;
+        else this.formatarDeclaracaoOuConstruto(declaracao.condicao);
 
         this.codigoFormatado += ` faca${this.quebraLinha}`;
         this.formatarDeclaracaoOuConstruto(declaracao.incrementar);
 
-        this.formatarBlocoOuVetorDeclaracoes(declaracao.corpo.declaracoes)
+        this.formatarBlocoOuVetorDeclaracoes(declaracao.corpo.declaracoes);
 
-        this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}fimpara${this.quebraLinha}`;
+        this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}fimpara${this.quebraLinha}`;
     }
     visitarDeclaracaoParaCada(declaracao: ParaCada): any {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarDeclaracaoSe(declaracao: Se) {
-        this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}se ( `;
+        this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}se ( `;
         this.formatarDeclaracaoOuConstruto(declaracao.condicao);
         this.codigoFormatado += ` ) entao${this.quebraLinha}`;
 
@@ -190,23 +240,23 @@ export class FormatadorVisualG implements VisitanteComumInterface {
 
         this.indentacaoAtual -= this.tamanhoIndentacao;
         if (declaracao.caminhoSenao) {
-            this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}} senao `;
+            this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}} senao `;
             this.formatarDeclaracaoOuConstruto(declaracao.caminhoSenao);
         } else {
-            this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}fimse${this.quebraLinha}`;
+            this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}fimse${this.quebraLinha}`;
         }
     }
     visitarDeclaracaoTente(declaracao: Tente) {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarDeclaracaoVar(declaracao: Var): any {
         switch (this.contadorDeclaracaoVar) {
             case 0:
-                this.codigoFormatado += `var${this.quebraLinha}`
+                this.codigoFormatado += `var${this.quebraLinha}`;
                 this.contadorDeclaracaoVar++;
                 break;
             case 2:
-                this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}var${this.quebraLinha}`
+                this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}var${this.quebraLinha}`;
                 this.contadorDeclaracaoVar++;
                 break;
         }
@@ -216,7 +266,7 @@ export class FormatadorVisualG implements VisitanteComumInterface {
         }
 
         if (this.deveIndentar) {
-            this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}`;
+            this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}`;
         }
 
         this.codigoFormatado += `${declaracao.simbolo.lexema}`;
@@ -233,54 +283,54 @@ export class FormatadorVisualG implements VisitanteComumInterface {
         }
     }
     visitarDeclaracaoVarMultiplo(declaracao: VarMultiplo): any {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarExpressaoAcessoIndiceVariavel(expressao: any) {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarExpressaoAcessoElementoMatriz(expressao: any) {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarExpressaoAcessoMetodo(expressao: any) {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarExpressaoAgrupamento(expressao: any): any {
-        this.codigoFormatado += "(";
+        this.codigoFormatado += '(';
         this.formatarDeclaracaoOuConstruto(expressao.expressao);
-        this.codigoFormatado += ")";
+        this.codigoFormatado += ')';
     }
     visitarExpressaoAtribuicaoPorIndice(expressao: any): any {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarExpressaoAtribuicaoPorIndicesMatriz(expressao: any): any {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarExpressaoBinaria(expressao: Binario) {
         this.formatarDeclaracaoOuConstruto(expressao.esquerda);
         switch (expressao.operador.tipo) {
             case tiposDeSimbolos.ADICAO:
-                this.codigoFormatado += " + "
+                this.codigoFormatado += ' + ';
                 break;
             case tiposDeSimbolos.DIVISAO:
-                this.codigoFormatado += " / "
+                this.codigoFormatado += ' / ';
                 break;
             case tiposDeSimbolos.DIVISAO_INTEIRA:
-                this.codigoFormatado += " \ "
+                this.codigoFormatado += '  ';
                 break;
             case tiposDeSimbolos.IGUAL:
-                this.codigoFormatado += " = "
+                this.codigoFormatado += ' = ';
                 break;
             case tiposDeSimbolos.MAIOR:
-                this.codigoFormatado += " > "
+                this.codigoFormatado += ' > ';
                 break;
             case tiposDeSimbolos.MAIOR_IGUAL:
-                this.codigoFormatado += " >= "
+                this.codigoFormatado += ' >= ';
                 break;
             case tiposDeSimbolos.MENOR:
-                this.codigoFormatado += "<"
+                this.codigoFormatado += '<';
                 break;
             case tiposDeSimbolos.MENOR_IGUAL:
-                this.codigoFormatado += " <= "
+                this.codigoFormatado += ' <= ';
                 break;
             case tiposDeSimbolos.SUBTRACAO:
                 this.codigoFormatado += ` - `;
@@ -294,9 +344,8 @@ export class FormatadorVisualG implements VisitanteComumInterface {
             default:
                 console.log(expressao.operador.tipo);
                 break;
-
         }
-        this.formatarDeclaracaoOuConstruto(expressao.direita)
+        this.formatarDeclaracaoOuConstruto(expressao.direita);
     }
 
     private formatarBlocoOuVetorDeclaracoes(declaracoes: Declaracao[]) {
@@ -311,64 +360,63 @@ export class FormatadorVisualG implements VisitanteComumInterface {
         this.formatarBlocoOuVetorDeclaracoes(declaracao.declaracoes);
     }
     visitarExpressaoContinua(declaracao?: Continua): ContinuarQuebra {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarExpressaoDeChamada(expressao: any) {
         this.formatarDeclaracaoOuConstruto(expressao.entidadeChamada);
-        this.codigoFormatado += "(";
+        this.codigoFormatado += '(';
         for (let argumento of expressao.argumentos) {
             this.formatarDeclaracaoOuConstruto(argumento);
-            this.codigoFormatado += ", ";
+            this.codigoFormatado += ', ';
         }
 
         if (expressao.argumentos.length > 0) {
             this.codigoFormatado = this.codigoFormatado.slice(0, -2);
         }
 
-        this.codigoFormatado += ")";
-
+        this.codigoFormatado += ')';
     }
     visitarExpressaoDefinirValor(expressao: any) {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarExpressaoDeleguaFuncao(expressao: any) {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarExpressaoDeVariavel(expressao: Variavel) {
         this.codigoFormatado += expressao.simbolo.lexema;
     }
     visitarExpressaoDicionario(expressao: any) {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarExpressaoExpressaoRegular(expressao: ExpressaoRegular): Promise<RegExp> {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarDeclaracaoEscrevaMesmaLinha(declaracao: EscrevaMesmaLinha) {
-        this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}escreva(`;
+        this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}escreva(`;
         for (let argumento of declaracao.argumentos) {
-            const argumentoTratado = argumento as FormatacaoEscrita
+            const argumentoTratado = argumento as FormatacaoEscrita;
             this.formatarDeclaracaoOuConstruto(argumentoTratado);
-            this.codigoFormatado += ", ";
+            this.codigoFormatado += ', ';
         }
-        if (declaracao.argumentos.length && this.codigoFormatado[this.codigoFormatado.length - 2] === ",") {
+        if (declaracao.argumentos.length && this.codigoFormatado[this.codigoFormatado.length - 2] === ',') {
             this.codigoFormatado = this.codigoFormatado.slice(0, -2);
         }
         this.codigoFormatado += `)${this.quebraLinha}`;
     }
     visitarExpressaoFalhar(expressao: any): any {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarExpressaoFimPara(declaracao: FimPara) {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarExpressaoFormatacaoEscrita(declaracao: FormatacaoEscrita) {
-        this.formatarDeclaracaoOuConstruto(declaracao.expressao)
+        this.formatarDeclaracaoOuConstruto(declaracao.expressao);
     }
     visitarExpressaoIsto(expressao: any) {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarExpressaoLeia(expressao: Leia): any {
-        this.codigoFormatado += `${" ".repeat(this.tamanhoIndentacao)}leia(`;
+        this.codigoFormatado += `${' '.repeat(this.tamanhoIndentacao)}leia(`;
         for (let argumento of expressao.argumentos) {
             this.formatarDeclaracaoOuConstruto(argumento);
             this.codigoFormatado += `, `;
@@ -381,13 +429,14 @@ export class FormatadorVisualG implements VisitanteComumInterface {
         this.codigoFormatado += `)${this.quebraLinha}`;
     }
     visitarExpressaoLeiaMultiplo(expressao: LeiaMultiplo): any {
-        return Promise.resolve()
+        return Promise.resolve();
     }
     visitarExpressaoLiteral(expressao: any): any {
-        if (typeof expressao.valor === "string") {
+        if (typeof expressao.valor === 'string') {
             this.codigoFormatado += `"${expressao.valor}"`;
             return;
-        } if (typeof expressao.valor === "boolean") {
+        }
+        if (typeof expressao.valor === 'boolean') {
             switch (expressao.valor) {
                 case true:
                     this.codigoFormatado += `verdadeiro`;
@@ -422,7 +471,7 @@ export class FormatadorVisualG implements VisitanteComumInterface {
         this.formatarDeclaracaoOuConstruto(expressao.direita);
     }
     visitarExpressaoRetornar(declaracao: Retorna): any {
-        this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}retorne`;
+        this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}retorne`;
         if (declaracao.valor) {
             this.codigoFormatado += ` `;
             this.formatarDeclaracaoOuConstruto(declaracao.valor);
@@ -431,15 +480,19 @@ export class FormatadorVisualG implements VisitanteComumInterface {
         this.codigoFormatado += `${this.quebraLinha}`;
     }
     visitarExpressaoSuper(expressao: Super) {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
     visitarExpressaoSustar(declaracao?: Sustar): any {
-        this.codigoFormatado += `${" ".repeat(this.indentacaoAtual)}interrompa${this.quebraLinha}`;
-
+        this.codigoFormatado += `${' '.repeat(this.indentacaoAtual)}interrompa${this.quebraLinha}`;
     }
     visitarExpressaoTipoDe(expressao: TipoDe): any {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
+    }
+
+    visitarExpressaoTupla(expressao: Tupla): Promise<any> {
+        throw new Error('Method not implemented.');
     }
+
     visitarExpressaoUnaria(expressao: Unario) {
         let operador: string;
         switch (expressao.operador.tipo) {
@@ -450,15 +503,15 @@ export class FormatadorVisualG implements VisitanteComumInterface {
                 operador = `+`;
                 break;
             case tiposDeSimbolos.NEGACAO:
-                operador = `nao `
+                operador = `nao `;
         }
 
         switch (expressao.incidenciaOperador) {
-            case "ANTES":
+            case 'ANTES':
                 this.codigoFormatado += operador;
                 this.formatarDeclaracaoOuConstruto(expressao.operando);
                 break;
-            case "DEPOIS":
+            case 'DEPOIS':
                 this.formatarDeclaracaoOuConstruto(expressao.operando);
                 this.codigoFormatado += operador;
                 break;
@@ -469,135 +522,135 @@ export class FormatadorVisualG implements VisitanteComumInterface {
         }
     }
     visitarExpressaoVetor(expressao: any) {
-        throw new Error("Método não implementado.");
+        throw new Error('Método não implementado.');
     }
 
     formatarDeclaracaoOuConstruto(declaracaoOuConstruto: Declaracao | Construto): void {
         switch (declaracaoOuConstruto.constructor.name) {
-            case "AcessoIndiceVariavel":
+            case 'AcessoIndiceVariavel':
                 this.visitarExpressaoAcessoIndiceVariavel(declaracaoOuConstruto as AcessoIndiceVariavel);
                 break;
-            case "AcessoMetodoOuPropriedade":
+            case 'AcessoMetodoOuPropriedade':
                 this.visitarExpressaoAcessoMetodo(declaracaoOuConstruto as AcessoMetodoOuPropriedade);
                 break;
-            case "Aleatorio":
+            case 'Aleatorio':
                 this.visitarDeclaracaoAleatorio(declaracaoOuConstruto as Aleatorio);
                 break;
-            case "Agrupamento":
+            case 'Agrupamento':
                 this.visitarExpressaoAgrupamento(declaracaoOuConstruto as Agrupamento);
                 break;
-            case "AtribuicaoPorIndice":
+            case 'AtribuicaoPorIndice':
                 this.visitarExpressaoAtribuicaoPorIndice(declaracaoOuConstruto as AtribuicaoPorIndice);
                 break;
-            case "Atribuir":
+            case 'Atribuir':
                 this.visitarExpressaoDeAtribuicao(declaracaoOuConstruto as Atribuir);
                 break;
-            case "Binario":
+            case 'Binario':
                 this.visitarExpressaoBinaria(declaracaoOuConstruto as Binario);
                 break;
-            case "Bloco":
+            case 'Bloco':
                 this.visitarExpressaoBloco(declaracaoOuConstruto as Bloco);
                 break;
-            case "Chamada":
+            case 'Chamada':
                 this.visitarExpressaoDeChamada(declaracaoOuConstruto as Chamada);
                 break;
-            case "Classe":
+            case 'Classe':
                 this.visitarDeclaracaoClasse(declaracaoOuConstruto as Classe);
                 break;
-            case "Continua":
+            case 'Continua':
                 this.visitarExpressaoContinua(declaracaoOuConstruto as Continua);
                 break;
-            case "DefinirValor":
+            case 'DefinirValor':
                 this.visitarExpressaoDefinirValor(declaracaoOuConstruto as DefinirValor);
                 break;
-            case "Dicionario":
+            case 'Dicionario':
                 this.visitarExpressaoDicionario(declaracaoOuConstruto as Dicionario);
                 break;
-            case "Escolha":
+            case 'Escolha':
                 this.visitarDeclaracaoEscolha(declaracaoOuConstruto as Escolha);
                 break;
-            case "Enquanto":
+            case 'Enquanto':
                 this.visitarDeclaracaoEnquanto(declaracaoOuConstruto as Enquanto);
                 break;
-            case "Escreva":
+            case 'Escreva':
                 this.visitarDeclaracaoEscreva(declaracaoOuConstruto as Escreva);
                 break;
-            case "EscrevaMesmaLinha":
+            case 'EscrevaMesmaLinha':
                 this.visitarDeclaracaoEscrevaMesmaLinha(declaracaoOuConstruto as Escreva);
                 break;
-            case "Expressao":
+            case 'Expressao':
                 this.visitarDeclaracaoDeExpressao(declaracaoOuConstruto as Expressao);
                 break;
-            case "ExpressaoRegular":
+            case 'ExpressaoRegular':
                 this.visitarExpressaoExpressaoRegular(declaracaoOuConstruto as ExpressaoRegular);
                 break;
-            case "Falhar":
-                this.visitarExpressaoFalhar(declaracaoOuConstruto as Falhar)
+            case 'Falhar':
+                this.visitarExpressaoFalhar(declaracaoOuConstruto as Falhar);
                 break;
-            case "Fazer":
+            case 'Fazer':
                 this.visitarDeclaracaoFazer(declaracaoOuConstruto as Fazer);
                 break;
-            case "FormatacaoEscrita":
+            case 'FormatacaoEscrita':
                 this.visitarExpressaoFormatacaoEscrita(declaracaoOuConstruto as FormatacaoEscrita);
                 break;
-            case "FuncaoConstruto":
+            case 'FuncaoConstruto':
                 this.visitarExpressaoFuncaoConstruto(declaracaoOuConstruto as FuncaoConstruto);
                 break;
-            case "FuncaoDeclaracao":
+            case 'FuncaoDeclaracao':
                 this.visitarDeclaracaoDefinicaoFuncao(declaracaoOuConstruto as FuncaoDeclaracao);
                 break;
-            case "Importar":
+            case 'Importar':
                 this.visitarDeclaracaoImportar(declaracaoOuConstruto as Importar);
                 break;
-            case "Isto":
+            case 'Isto':
                 this.visitarExpressaoIsto(declaracaoOuConstruto as Isto);
                 break;
-            case "Leia":
+            case 'Leia':
                 this.visitarExpressaoLeia(declaracaoOuConstruto as Leia);
                 break;
-            case "Literal":
+            case 'Literal':
                 this.visitarExpressaoLiteral(declaracaoOuConstruto as Literal);
                 break;
-            case "Logico":
+            case 'Logico':
                 this.visitarExpressaoLogica(declaracaoOuConstruto as Logico);
                 break;
-            case "Para":
+            case 'Para':
                 this.visitarDeclaracaoPara(declaracaoOuConstruto as Para);
                 break;
-            case "ParaCada":
+            case 'ParaCada':
                 this.visitarDeclaracaoParaCada(declaracaoOuConstruto as ParaCada);
                 break;
-            case "Retorna":
+            case 'Retorna':
                 this.visitarExpressaoRetornar(declaracaoOuConstruto as Retorna);
                 break;
-            case "Se":
+            case 'Se':
                 this.visitarDeclaracaoSe(declaracaoOuConstruto as Se);
                 break;
-            case "Super":
+            case 'Super':
                 this.visitarExpressaoSuper(declaracaoOuConstruto as Super);
                 break;
-            case "Sustar":
+            case 'Sustar':
                 this.visitarExpressaoSustar(declaracaoOuConstruto as Sustar);
                 break;
-            case "Tente":
+            case 'Tente':
                 this.visitarDeclaracaoTente(declaracaoOuConstruto as Tente);
                 break;
-            case "TipoDe":
+            case 'TipoDe':
                 this.visitarExpressaoTipoDe(declaracaoOuConstruto as TipoDe);
                 break;
-            case "Unario":
+            case 'Unario':
                 this.visitarExpressaoUnaria(declaracaoOuConstruto as Unario);
                 break;
-            case "Const":
+            case 'Const':
                 this.visitarDeclaracaoConst(declaracaoOuConstruto as Const);
                 break;
-            case "Var":
+            case 'Var':
                 this.visitarDeclaracaoVar(declaracaoOuConstruto as Var);
                 break;
-            case "Variavel":
+            case 'Variavel':
                 this.visitarExpressaoDeVariavel(declaracaoOuConstruto as Variavel);
                 break;
-            case "Vetor":
+            case 'Vetor':
                 this.visitarExpressaoVetor(declaracaoOuConstruto as Vetor);
                 break;
             default:
@@ -609,8 +662,9 @@ export class FormatadorVisualG implements VisitanteComumInterface {
         if (expressao.parametros.length > 0) {
             this.codigoFormatado += `(`;
             for (let argumento of expressao.parametros) {
-                this.codigoFormatado += `${argumento.nome.lexema}${argumento.tipoDado && argumento.tipoDado.tipo ? `: ${argumento.tipoDado.tipo}, ` : ", "
-                    }`;
+                this.codigoFormatado += `${argumento.nome.lexema}${
+                    argumento.tipoDado && argumento.tipoDado.tipo ? `: ${argumento.tipoDado.tipo}, ` : ', '
+                }`;
             }
             this.codigoFormatado = this.codigoFormatado.slice(0, -2);
             this.codigoFormatado += `) `;
@@ -628,17 +682,15 @@ export class FormatadorVisualG implements VisitanteComumInterface {
 
         for (let declaracao of declaracoes) {
             if (!(declaracao instanceof Var) && this.deveAdicionarInicio) {
-                this.codigoFormatado += `${this.quebraLinha}inicio${this.quebraLinha}`
+                this.codigoFormatado += `${this.quebraLinha}inicio${this.quebraLinha}`;
                 this.deveAdicionarInicio = false;
-            } else if (declaracao instanceof Var) this.deveAdicionarInicio = true
-
+            } else if (declaracao instanceof Var) this.deveAdicionarInicio = true;
 
             this.formatarDeclaracaoOuConstruto(declaracao);
         }
 
         this.indentacaoAtual -= this.tamanhoIndentacao;
-        this.codigoFormatado += `${this.quebraLinha}fimalgoritmo`
+        this.codigoFormatado += `${this.quebraLinha}fimalgoritmo`;
         return this.codigoFormatado;
     }
-
-}
\ No newline at end of file
+}
diff --git a/fontes/interfaces/pilha-escopos-execucao-interface.ts b/fontes/interfaces/pilha-escopos-execucao-interface.ts
index f0788f59..ea6bba55 100644
--- a/fontes/interfaces/pilha-escopos-execucao-interface.ts
+++ b/fontes/interfaces/pilha-escopos-execucao-interface.ts
@@ -8,7 +8,7 @@ export interface PilhaEscoposExecucaoInterface extends PilhaInterface<EscopoExec
     atribuirVariavel(simbolo: SimboloInterface, valor: any): void;
     atribuirVariavelEm(distancia: number, simbolo: SimboloInterface, valor: any): void;
     definirConstante(nomeConstante: string, valor: any, subtipo?: string): void;
-    definirVariavel(nomeVariavel: string, valor: any, subtipo?: string): void;
+    definirVariavel(nomeVariavel: string, valor: any, subtipo?: string, imutavel?: boolean): void;
     elementos(): number;
     naPosicao(posicao: number): EscopoExecucao;
     obterEscopoPorTipo(idChamada: string): EscopoExecucao | undefined;
diff --git a/fontes/interfaces/visitante-comum-interface.ts b/fontes/interfaces/visitante-comum-interface.ts
index 2e80d408..6f75c214 100644
--- a/fontes/interfaces/visitante-comum-interface.ts
+++ b/fontes/interfaces/visitante-comum-interface.ts
@@ -1,4 +1,4 @@
-import { AcessoMetodoOuPropriedade, Atribuir, ExpressaoRegular, FimPara, Literal, Super, TipoDe } from '../construtos';
+import { AcessoMetodoOuPropriedade, Atribuir, ExpressaoRegular, FimPara, Literal, Super, TipoDe, Tupla } from '../construtos';
 import {
     Aleatorio,
     Bloco,
@@ -75,6 +75,7 @@ export interface VisitanteComumInterface {
     visitarExpressaoRetornar(declaracao: Retorna): Promise<RetornoQuebra>;
     visitarExpressaoSuper(expressao: Super): any;
     visitarExpressaoSustar(declaracao?: Sustar): SustarQuebra;
+    visitarExpressaoTupla(expressao: Tupla): Promise<any>;
     visitarExpressaoTipoDe(expressao: TipoDe): Promise<any>;
     visitarExpressaoUnaria(expressao: any): any;
     visitarExpressaoVetor(expressao: any): any;
diff --git a/fontes/interpretador/dialetos/egua-classico/interpretador-egua-classico.ts b/fontes/interpretador/dialetos/egua-classico/interpretador-egua-classico.ts
index 0a7b2fbe..be785092 100644
--- a/fontes/interpretador/dialetos/egua-classico/interpretador-egua-classico.ts
+++ b/fontes/interpretador/dialetos/egua-classico/interpretador-egua-classico.ts
@@ -18,6 +18,7 @@ import {
     QualTipo,
     Super,
     TipoDe,
+    Tupla,
     Variavel,
 } from '../../../construtos';
 import {
@@ -98,6 +99,9 @@ export class InterpretadorEguaClassico implements InterpretadorInterface {
 
         carregarBibliotecaGlobal(this, this.pilhaEscoposExecucao);
     }
+    visitarExpressaoTupla(expressao: Tupla): Promise<any> {
+        throw new Error('Método não implementado.');
+    }
     visitarExpressaoAcessoElementoMatriz(expressao: any) {
         throw new Error('Método não implementado.');
     }
diff --git a/fontes/interpretador/dialetos/egua-classico/resolvedor/resolvedor.ts b/fontes/interpretador/dialetos/egua-classico/resolvedor/resolvedor.ts
index 2683cca1..7aebfb1e 100644
--- a/fontes/interpretador/dialetos/egua-classico/resolvedor/resolvedor.ts
+++ b/fontes/interpretador/dialetos/egua-classico/resolvedor/resolvedor.ts
@@ -1,4 +1,4 @@
-import { AcessoMetodoOuPropriedade, Construto, ExpressaoRegular, FimPara, FormatacaoEscrita, QualTipo, Super, TipoDe, Variavel } from '../../../../construtos';
+import { AcessoMetodoOuPropriedade, Construto, ExpressaoRegular, FimPara, FormatacaoEscrita, QualTipo, Super, TipoDe, Tupla, Variavel } from '../../../../construtos';
 import {
     Aleatorio,
     Bloco,
@@ -76,6 +76,9 @@ export class ResolvedorEguaClassico implements ResolvedorInterface, Interpretado
         this.classeAtual = TipoClasse.NENHUM;
         this.cicloAtual = TipoClasse.NENHUM;
     }
+    visitarExpressaoTupla(expressao: Tupla): Promise<any> {
+        throw new Error('Método não implementado.');
+    }
     visitarExpressaoAcessoElementoMatriz(expressao: any) {
         throw new Error('Método não implementado.');
     }
diff --git a/fontes/interpretador/dialetos/portugol-ipt/interpretador-portugol-ipt.ts b/fontes/interpretador/dialetos/portugol-ipt/interpretador-portugol-ipt.ts
index bf16561b..d468c222 100644
--- a/fontes/interpretador/dialetos/portugol-ipt/interpretador-portugol-ipt.ts
+++ b/fontes/interpretador/dialetos/portugol-ipt/interpretador-portugol-ipt.ts
@@ -1,4 +1,4 @@
-import { Atribuir, Construto, ExpressaoRegular, FimPara, FormatacaoEscrita, Literal, QualTipo, Super, TipoDe, Variavel } from '../../../construtos';
+import { Atribuir, Construto, ExpressaoRegular, FimPara, FormatacaoEscrita, Literal, QualTipo, Super, TipoDe, Tupla, Variavel } from '../../../construtos';
 import {
     Aleatorio,
     Bloco,
@@ -74,6 +74,9 @@ export class InterpretadorPortugolIpt implements InterpretadorInterface {
         };
         this.pilhaEscoposExecucao.empilhar(escopoExecucao);
     }
+    visitarExpressaoTupla(expressao: Tupla): Promise<any> {
+        throw new Error('Método não implementado.');
+    }
     visitarExpressaoAcessoElementoMatriz(expressao: any) {
         throw new Error('Método não implementado.');
     }
diff --git a/fontes/interpretador/interpretador-base.ts b/fontes/interpretador/interpretador-base.ts
index 39d10661..34344e5b 100644
--- a/fontes/interpretador/interpretador-base.ts
+++ b/fontes/interpretador/interpretador-base.ts
@@ -60,6 +60,7 @@ import {
     QualTipo,
     Super,
     TipoDe,
+    Tupla,
     Unario,
     Variavel,
     Vetor,
@@ -160,6 +161,17 @@ export class InterpretadorBase implements InterpretadorInterface {
         carregarBibliotecasGlobais(this, this.pilhaEscoposExecucao);
     }
 
+    async visitarExpressaoTupla(expressao: any): Promise<any> {
+        const chaves = Object.keys(expressao)
+        const valores = [];
+        for (let chave of chaves) {
+            const valor = await this.avaliar(expressao[chave])
+            valores.push(valor);
+        }
+
+        return valores;
+    }
+
     visitarExpressaoAtribuicaoPorIndicesMatriz(expressao: any): Promise<any> {
         throw new Error('Método não implementado.');
     }
@@ -168,7 +180,6 @@ export class InterpretadorBase implements InterpretadorInterface {
         throw new Error('Método não implementado.');
     }
 
-    //https://stackoverflow.com/a/66751666/9043143
     protected textoParaRegex(texto: string): RegExp {
         const match = texto.match(/^([\/~@;%#'])(.*?)\1([gimsuy]*)$/);
         return match
@@ -1190,6 +1201,16 @@ export class InterpretadorBase implements InterpretadorInterface {
         let indice = promises[1];
         const valor = promises[2];
 
+        if (objeto.imutavel) {
+            return Promise.reject(
+                new ErroEmTempoDeExecucao(
+                    expressao.objeto.simbolo.lexema,
+                    'Não é possível modificar uma tupla. As tuplas são estruturas de dados imutáveis.',
+                    expressao.linha
+                )
+            );
+        }
+
         objeto = objeto.hasOwnProperty('valor') ? objeto.valor : objeto;
         indice = indice.hasOwnProperty('valor') ? indice.valor : indice;
 
@@ -1518,11 +1539,13 @@ export class InterpretadorBase implements InterpretadorInterface {
         const valorFinal = await this.avaliacaoDeclaracaoVarOuConst(declaracao);
 
         let subtipo;
-        if (declaracao.tipo !== undefined) {
+        if (declaracao.tipo !== undefined && declaracao.tipo !== null) {
             subtipo = declaracao.tipo;
         }
+        
+        const eTupla = declaracao.inicializador instanceof Tupla;
 
-        this.pilhaEscoposExecucao.definirVariavel(declaracao.simbolo.lexema, valorFinal, subtipo);
+        this.pilhaEscoposExecucao.definirVariavel(declaracao.simbolo.lexema, valorFinal, subtipo, eTupla);
 
         return null;
     }
diff --git a/fontes/interpretador/pilha-escopos-execucao.ts b/fontes/interpretador/pilha-escopos-execucao.ts
index 5c5cf406..bf357202 100644
--- a/fontes/interpretador/pilha-escopos-execucao.ts
+++ b/fontes/interpretador/pilha-escopos-execucao.ts
@@ -77,7 +77,7 @@ export class PilhaEscoposExecucao implements PilhaEscoposExecucaoInterface {
         this.pilha[this.pilha.length - 1].ambiente.valores[nomeConstante] = elementoAlvo;
     }
 
-    definirVariavel(nomeVariavel: string, valor: any, subtipo?: string) {
+    definirVariavel(nomeVariavel: string, valor: any, subtipo?: string, imutavel: boolean = false) {
         const variavel = this.pilha[this.pilha.length - 1].ambiente.valores[nomeVariavel];
         let tipo = variavel && variavel.hasOwnProperty('tipo') ? variavel.tipo : inferirTipoVariavel(valor);
         // TODO: Dois testes no VisuAlg falham por causa disso.
@@ -91,7 +91,7 @@ export class PilhaEscoposExecucao implements PilhaEscoposExecucaoInterface {
             valor: this.converterValor(tipo, valor),
             tipo: tipo,
             subtipo: undefined,
-            imutavel: false,
+            imutavel: imutavel,
         };
 
         if (subtipo !== undefined) {


Test patch:
diff --git a/testes/interpretador.test.ts b/testes/interpretador.test.ts
index 9d38a6ee..35d46f30 100644
--- a/testes/interpretador.test.ts
+++ b/testes/interpretador.test.ts
@@ -1550,6 +1550,20 @@ describe('Interpretador', () => {
                         'Constante \'c\' não pode receber novos valores.'
                     );
                 });
+
+                it('Tupla - Dupla', async () => {
+                    const retornoLexador = lexador.mapear([
+                        "var t = [(1, 2)]",
+                        "t[0] = 3",
+                    ], -1);
+                    const retornoAvaliadorSintatico = avaliadorSintatico.analisar(retornoLexador, -1);
+
+                    const retornoInterpretador = await interpretador.interpretar(retornoAvaliadorSintatico.declaracoes);
+
+                    expect(retornoInterpretador.erros[0].erroInterno.mensagem).toBe(
+                        'Não é possível modificar uma tupla. As tuplas são estruturas de dados imutáveis.'
+                    );
+                });
             })
         });
     });
diff --git a/testes/visualg/formatador-visualg.test.ts b/testes/visualg/formatador-visualg.test.ts
index c330fbba..16d1761f 100644
--- a/testes/visualg/formatador-visualg.test.ts
+++ b/testes/visualg/formatador-visualg.test.ts
@@ -1,11 +1,11 @@
 import * as sistemaOperacional from 'os';
 
-import { FormatadorVisualG } from '../../fontes/formatadores';
+import { FormatadorVisuAlg } from '../../fontes/formatadores';
 import { LexadorVisuAlg } from '../../fontes/lexador/dialetos';
 import { AvaliadorSintaticoVisuAlg } from '../../fontes/avaliador-sintatico/dialetos';
 
 describe('Formatadores > VisualG', () => {
-    const formatadorVisualG = new FormatadorVisualG(sistemaOperacional.EOL);
+    const formatadorVisuAlg = new FormatadorVisuAlg(sistemaOperacional.EOL);
     const avaliadorSintaticoVisualG = new AvaliadorSintaticoVisuAlg();
     const lexadorVisuAlg = new LexadorVisuAlg();
 
@@ -19,7 +19,7 @@ describe('Formatadores > VisualG', () => {
 
         const retornoAvaliadorSintatico = avaliadorSintaticoVisualG.analisar(retornoLexador, -1);
 
-        const resultado = formatadorVisualG.formatar(retornoAvaliadorSintatico.declaracoes);
+        const resultado = formatadorVisuAlg.formatar(retornoAvaliadorSintatico.declaracoes);
         const linhasResultado = resultado.split(sistemaOperacional.EOL)
 
         expect(linhasResultado).toHaveLength(6)
@@ -42,7 +42,7 @@ describe('Formatadores > VisualG', () => {
 
         const retornoAvaliadorSintatico = avaliadorSintaticoVisualG.analisar(retornoLexador, -1);
 
-        const resultado = formatadorVisualG.formatar(retornoAvaliadorSintatico.declaracoes);
+        const resultado = formatadorVisuAlg.formatar(retornoAvaliadorSintatico.declaracoes);
         const linhasResultado = resultado.split(sistemaOperacional.EOL)
 
         expect(linhasResultado).toHaveLength(13)
@@ -65,7 +65,7 @@ describe('Formatadores > VisualG', () => {
         );
 
         const retornoAvaliadorSintatico = avaliadorSintaticoVisualG.analisar(retornoLexador, -1);
-        const resultado = formatadorVisualG.formatar(retornoAvaliadorSintatico.declaracoes);
+        const resultado = formatadorVisuAlg.formatar(retornoAvaliadorSintatico.declaracoes);
 
         const linhasResultado = resultado.split(sistemaOperacional.EOL)
         expect(linhasResultado).toHaveLength(11)
@@ -88,7 +88,7 @@ describe('Formatadores > VisualG', () => {
         );
 
         const retornoAvaliadorSintatico = avaliadorSintaticoVisualG.analisar(retornoLexador, -1);
-        const resultado = formatadorVisualG.formatar(retornoAvaliadorSintatico.declaracoes);
+        const resultado = formatadorVisuAlg.formatar(retornoAvaliadorSintatico.declaracoes);
 
         const linhasResultado = resultado.split(sistemaOperacional.EOL)
         expect(linhasResultado).toHaveLength(10)
@@ -115,7 +115,7 @@ describe('Formatadores > VisualG', () => {
             -1
         );
         const retornoAvaliadorSintatico = avaliadorSintaticoVisualG.analisar(retornoLexador, -1);
-        const resultado = formatadorVisualG.formatar(retornoAvaliadorSintatico.declaracoes);
+        const resultado = formatadorVisuAlg.formatar(retornoAvaliadorSintatico.declaracoes);
 
         const linhasResultado = resultado.split(sistemaOperacional.EOL)
         expect(linhasResultado).toHaveLength(16)
@@ -146,7 +146,7 @@ describe('Formatadores > VisualG', () => {
         );
         const retornoAvaliadorSintatico = avaliadorSintaticoVisualG.analisar(retornoLexador, -1);
 
-        const resultado = formatadorVisualG.formatar(retornoAvaliadorSintatico.declaracoes);
+        const resultado = formatadorVisuAlg.formatar(retornoAvaliadorSintatico.declaracoes);
 
         const linhasResultado = resultado.split(sistemaOperacional.EOL)
         expect(linhasResultado).toHaveLength(22)
@@ -171,7 +171,7 @@ describe('Formatadores > VisualG', () => {
             -1
         );
         const retornoAvaliadorSintatico = avaliadorSintaticoVisualG.analisar(retornoLexador, -1);
-        const resultado = formatadorVisualG.formatar(retornoAvaliadorSintatico.declaracoes)
+        const resultado = formatadorVisuAlg.formatar(retornoAvaliadorSintatico.declaracoes)
         const linhasResultado = resultado.split(sistemaOperacional.EOL)
 
         expect(linhasResultado).toHaveLength(13)
@@ -200,7 +200,7 @@ describe('Formatadores > VisualG', () => {
         );
 
         const retornoAvaliadorSintatico = avaliadorSintaticoVisualG.analisar(retornoLexador, -1);
-        const resultado = formatadorVisualG.formatar(retornoAvaliadorSintatico.declaracoes)
+        const resultado = formatadorVisuAlg.formatar(retornoAvaliadorSintatico.declaracoes)
         const linhasResultado = resultado.split(sistemaOperacional.EOL)
 
         expect(linhasResultado).toHaveLength(12)
@@ -223,7 +223,7 @@ describe('Formatadores > VisualG', () => {
             -1
         );
         const retornoAvaliadorSintatico = avaliadorSintaticoVisualG.analisar(retornoLexador, -1);
-        const resultado = formatadorVisualG.formatar(retornoAvaliadorSintatico.declaracoes)
+        const resultado = formatadorVisuAlg.formatar(retornoAvaliadorSintatico.declaracoes)
         const linhasResultado = resultado.split(sistemaOperacional.EOL)
 
         expect(linhasResultado).toHaveLength(9)
@@ -279,7 +279,7 @@ describe('Formatadores > VisualG', () => {
             -1
         );
         const retornoAvaliadorSintatico = avaliadorSintaticoVisualG.analisar(retornoLexador, -1);
-        const resultado = formatadorVisualG.formatar(retornoAvaliadorSintatico.declaracoes)
+        const resultado = formatadorVisuAlg.formatar(retornoAvaliadorSintatico.declaracoes)
         const linhasResultado = resultado.split(sistemaOperacional.EOL)
 
         expect(linhasResultado).toHaveLength(10);
@@ -314,7 +314,7 @@ describe('Formatadores > VisualG', () => {
             -1
         );
         const retornoAvaliadorSintatico = avaliadorSintaticoVisualG.analisar(retornoLexador, -1);
-        const resultado = formatadorVisualG.formatar(retornoAvaliadorSintatico.declaracoes)
+        const resultado = formatadorVisuAlg.formatar(retornoAvaliadorSintatico.declaracoes)
         const linhasResultado = resultado.split(sistemaOperacional.EOL)
 
         expect(linhasResultado).toHaveLength(29);
@@ -339,7 +339,7 @@ describe('Formatadores > VisualG', () => {
         const retornoAvaliadorSintatico = avaliadorSintaticoVisualG.analisar(retornoLexador, -1);
 
 
-        const resultado = formatadorVisualG.formatar(retornoAvaliadorSintatico.declaracoes)
+        const resultado = formatadorVisuAlg.formatar(retornoAvaliadorSintatico.declaracoes)
         const linhasResultado = resultado.split(sistemaOperacional.EOL)
 
         expect(linhasResultado).toHaveLength(8);