private void ConverterParaPosfixa(FilaLista <char> seqInfixa, ref string posfixa) { char operadorComMaiorPrecedencia; PilhaLista <char> pilha = new PilhaLista <char>(); //pilha que será usada para empilhar operadores do { char simboloLido = seqInfixa.Retirar(); //simbolo lido é retirado da fila de sequencia infixa if (!(simboloLido <= 'Z' && simboloLido >= 'A')) //se o simbolo lido não estiver entre A e Z, ou seja, for um operador { if (pilha.EstaVazia()) //se a pilha estiver vazia, empilha-se simbolo lido { pilha.Empilhar(simboloLido); } else //se não estiver vazia { while (!pilha.EstaVazia() && DeveDesempilhar(pilha.OTopo(), simboloLido)) //enquanto a pilha não estiver vazia e deve desempilhar, ou seja, o topo da pilha tem precedencia sobre o simbolo lido { operadorComMaiorPrecedencia = pilha.Desempilhar(); //armazena-se operador com maior precedencia, tirando-o do topo if (operadorComMaiorPrecedencia != '(') //caso não seja '(', pois não se coloca parêntesis em sequências posfixas { seqPosfixa.Enfileirar(operadorComMaiorPrecedencia); //enfileira-se na seqPosfixa posfixa += operadorComMaiorPrecedencia; //concatena-se na string de posfixa } } if (simboloLido != ')') // empilha-se o simbolo lido, a menos que ele seja um ')' { pilha.Empilhar(simboloLido); } else { if (!pilha.EstaVazia() && pilha.OTopo() == '(') //se o simbolo lido for ')' e já foi feito o método acima sobre as precedencias, restará um parentesis aberto no topo da pilha, a menos que a sequência não esteja balanceada { operadorComMaiorPrecedencia = pilha.Desempilhar(); } else { erro = true; } } } } else // se for letra { seqPosfixa.Enfileirar(simboloLido); //enfileira-se letra na sequência posfixa += simboloLido; //concatena-se a letra na string posfixa } }while (!seqInfixa.EstaVazia() && !erro); //enquando não estiver vazia e não houver nenhum erro, continua-se a expressão while (!pilha.EstaVazia() && !erro) // se a fila de sequência ja estiver acabado mas houver operandos na pilha e não tiver dado erro { operadorComMaiorPrecedencia = pilha.Desempilhar(); //desempilha-se elemento da pilha if (operadorComMaiorPrecedencia != '(') //se não for '(' { seqPosfixa.Enfileirar(operadorComMaiorPrecedencia); //enfileira elemento posfixa += operadorComMaiorPrecedencia; //concatena à string posfixa } } }
private void Converter(string inf) { string elemento = ""; string op = ""; for (int i = 0; i < inf.Length; i++) //Passa por todos os itens da sequencia infixa { elemento = ""; if (!ops.Contains(inf[i])) //Se o item lido não for um operador { elemento = ""; int inicial = i; //index do início do numero while (inicial + elemento.Length < inf.Length && (!ops.Contains(inf[inicial + elemento.Length].ToString()) || inf[inicial + elemento.Length] == '.')) //Enquanto o elemento ainda for um número { elemento += inf[inicial + elemento.Length]; //O número é incrementado } i = inicial + elemento.Length - 1; //o for continua a partir de onde a leitura parou posfixa.Enfileirar(elemento); //O número é adicionado na fila posfixa } else //Se o item lido for um operador { elemento = inf[i].ToString(); //O elemento recebe o item lido while (!pilOps.EstaVazia() && Precedencia(pilOps.OTopo()) >= Precedencia(elemento[0].ToString())) //Enquanto o primeiro operador da pilha tiver precedência sobre os outros { op = pilOps.OTopo(); //Identifica o operador a ser tratado if (op == "(") { break; } posfixa.Enfileirar(op.ToString()); //O operador é adicionado na sequencia posfixa pilOps.Desempilhar(); //E removido da pilha } if (elemento == ")") //Se o operador for o fecha parênteses { pilOps.Desempilhar(); //Desempilha o ultimo operador } else //Se não { pilOps.Empilhar(elemento); //Empilha o operador normalmente } } if (elemento != "(" && elemento != ")") //Verifica se o item não é ( nem ), pois esses não entram na sequência { infixa.Enfileirar(elemento); //Adiciona o item na infixa } } while (!pilOps.EstaVazia()) //Até a pilha ficar vazia { op = pilOps.Desempilhar(); //Desempilha o operador if (op != "(" && op != ")") //Verifica se o item não é ( nem ), pois esses não entram na sequência { posfixa.Enfileirar(op); //Enfilera o operador na posfixa } } }
//private string ParaPosfixa(string infixa) //{ // string ret = ""; // char[] exp = infixa.ToCharArray(); // string ops = "()^*/+-"; // PilhaLista<char> seq = new PilhaLista<char>(); // //foreach (char c in exp) // //{ // // if (ops.Contains(c)) // // { // // if (seq.EstaVazia()) // // seq.Empilhar(c); // // else // // { // // if (MaiorPrecedencia(seq.OTopo(), c) == seq.OTopo()) // // { // // if (c == ')') // // { // // while (!seq.EstaVazia() && seq.OTopo() != '(') // // ret += seq.Desempilhar(); // // } // // else // // { // // ret += seq.Desempilhar(); // // seq.Empilhar(c); // // } // // } // // else // // seq.Empilhar(c); // // } // // } // // else // // ret += c; // //} // for (int i=0; i<infixa.Length; i++) // { // char c = infixa[i]; // if (ops.Contains(c)) // { // if (seq.EstaVazia()) // { // seq.Empilhar(c); // } // else // { // if (MaiorPrecedencia(seq.OTopo(), c) == seq.OTopo()) // { // if (c == '+' || c == '-') // { // ret += seq.Desempilhar(); // i--; // } // else // { // ret += seq.Desempilhar(); // i--; // } // } // else // { // if (c == '+' || c == '-') // { // ret += seq.Desempilhar(); // seq.Empilhar(c); // } // else // { // seq.Empilhar(c); // } // } // } // } // else // { // ret += c; // } // } // return ret; //} //public string ParaPosfixa(string inf) //{ // string ret = ""; // char[] exp = inf.ToCharArray(); // string ops = "()^*/+-"; // PilhaLista<string> pilOps = new PilhaLista<string>(); // for (int i = 0; i < inf.Length; i++) // { // string elemento = ""; // if (!ops.Contains(inf[i].ToString())) // { // elemento = ""; // int inicial = i; // while (inicial + elemento.Length < inf.Length && (!ops.Contains(inf[inicial + elemento.Length].ToString()) || inf[inicial + elemento.Length] == '.')) // elemento += inf[inicial + elemento.Length]; // i = inicial + elemento.Length - 1; // //posfixa.Enfileirar(elemento); // } // else // { // if (inf[i] == '+' && (i == 0 || inf[i - 1] == '(')) // elemento = "#"; // else // if (inf[i] == '-' && (i == 0 || inf[i - 1] == '(')) // elemento = "@"; // else // elemento = inf[i] + ""; // while (!pilOps.EstaVazia() && Precedencia(pilOps.OTopo()[0] )> Precedencia (elemento[0])) // { // string op = pilOps.Desempilhar(); // /*if (op != "(" && op != ")") // posfixa.Enfileirar(op);*/ // } // if (elemento != ")") // pilOps.Empilhar(elemento); // } // if (elemento != "(" && elemento != ")") // ret += elemento; // //infixa.Enfileirar(elemento); // } // //TratarPilhaOperadores(); // while (!pilOps.EstaVazia()) // { // string o = pilOps.Desempilhar(); // ret += o; // } // //sequenciaInfixa = EscreverSequencia(infixa); // //sequenciaPosfixa = EscreverSequencia(posfixa); // //resultado = CalcularResultado(); // //return resultado; // return ret; //} private void Converter(string inf) { for (int i = 0; i < inf.Length; i++) { string elemento = ""; if (ops.Contains(inf[i])) { elemento = ""; int inicial = i; while (inicial + elemento.Length < inf.Length && (!ops.Contains(inf[inicial + elemento.Length].ToString()) || inf[inicial + elemento.Length] == '.')) { elemento += inf[inicial + elemento.Length]; } i = inicial + elemento.Length - 1; posfixa.Enfileirar(elemento); } else { elemento = inf[i].ToString(); while (!pilOps.EstaVazia() && Precedencia(pilOps.OTopo()) > Precedencia(elemento[0].ToString())) { char op = pilOps.OTopo()[0]; if (op == '(') { break; } posfixa.Enfileirar(op.ToString()); pilOps.Desempilhar(); } if (elemento != ")") { pilOps.Empilhar(elemento); } else { pilOps.Desempilhar(); } } if (elemento != "(" && elemento != ")") { infixa.Enfileirar(elemento); } } while (!pilOps.EstaVazia()) { string op = pilOps.Desempilhar(); if (op != "(" && op != ")") { posfixa.Enfileirar(op); } } }
// MÉTODO PARA TRANSFORMAR A EXPRESSÃO INFIXA PARA PÓSFIXA private static void InfixaParaPosfixa(string expLetras, ref string expPosfixa) { PilhaLista <char> pilha = new PilhaLista <char>(); // para empilhar os operadores expPosfixa = ""; // expressão pósfixa com letras for (int posExp = 0; posExp < expLetras.Length; posExp++) { char c = Convert.ToChar(expLetras.Substring(posExp, 1)); // caracter lido if (!IsOperador(c)) // se não é operador, ou seja, é letra (valor) { expPosfixa += c; // adiciona na expressão } else { if (pilha.EstaVazia() && c != ')') { pilha.Empilhar(c); // empilha o operador } else { if (c == ')') // se achamos um ")", existem operações prioritárias { while (pilha.OTopo() != '(') // enquanto não acharmos o correspondente { expPosfixa += pilha.Desempilhar(); // desempilha os operadores priorizados } pilha.Desempilhar(); // desempilha o próprio "(" } else { while (Precedencia(pilha.OTopo(), c) && pilha.OTopo() != '(') { expPosfixa += pilha.Desempilhar(); // o topo tem precedência, então devem vir primeiro (desempilhando) if (pilha.EstaVazia()) { break; } } pilha.Empilhar(c); // empilha o novo caracter lido } } } } while (!pilha.EstaVazia()) // acabou a expressão, então se sobrou operadores { expPosfixa += pilha.Desempilhar(); // desempilhamos, já que está na ordem certa } }
private string paraPosfixa(string infixa) { string ret = ""; char[] exp = infixa.ToCharArray(); string ops = "()^*/+-"; PilhaLista <char> seq = new PilhaLista <char>(); foreach (char c in exp) { if (ops.Contains(c)) { if (seq.EstaVazia()) { seq.Empilhar(c); } else { if (MaiorPrecedencia(seq.OTopo(), c) == seq.OTopo()) { if (c == ')') { while (!seq.EstaVazia() && seq.OTopo() != '(') { ret += seq.Desempilhar(); } } else { ret += seq.Desempilhar(); seq.Empilhar(c); } } else { seq.Empilhar(c); } } } else { ret += c; } } return(ret); }
private void btnIgual_Click(object sender, EventArgs e) { FilaLista <string> infixa = new FilaLista <string>(); FilaLista <string> posfixa = new FilaLista <string>(); PilhaLista <string> ops = new PilhaLista <string>(); //declara e instancia as 3 listas string expressao = txtVisor.Text; //expressão a ser calculada for (int i = 0; i < expressao.Length; i++) //for até o fim da expressão { string elemento = ""; if (!IsOp(expressao[i].ToString())) //se não for uma operção { elemento = ""; int inicial = i; while (inicial + elemento.Length < expressao.Length && (!IsOp(expressao[inicial + elemento.Length].ToString()) || expressao[inicial + elemento.Length] == '.')) //enquanto não acabou a expressão, não for operação ou não for ponto { elemento += expressao[inicial + elemento.Length]; //incrementa o elemento com o valor da posição específic da expressão } i = inicial + elemento.Length - 1; posfixa.Enfileirar(elemento); //enfileira na posfixa o elemento } else //se for operação { elemento = expressao[i] + ""; while (!ops.EstaVazia() && TemPrecedencia(ops.OTopo()[0], elemento[0])) //enquanto não estiver vazia e tiver precedência { char op = ops.OTopo()[0]; if (op == '(') { break; } else //se não for abre parenteses { posfixa.Enfileirar(op + ""); //enfileira ops.Desempilhar(); //desempilha } } if (elemento != ")") //se não for fecha parenteses { ops.Empilhar(elemento); //empilha } else //se for { ops.Desempilhar(); //desempilha } } if (elemento != "(" && elemento != ")") //se não for parenteses { infixa.Enfileirar(elemento); //enfileira o elemento } } while (!ops.EstaVazia()) //enquanto não estiver vazia { string op = ops.Desempilhar(); //pega o primeiro da pilha if (op != "(" && op != ")") //se não for parenteses { posfixa.Enfileirar(op); //enfileira } } escreverSeq(infixa, posfixa); //escreve na tela as sequências txtResultado.Text = CalcularResultado(posfixa).ToString(); //calcula e escreve o resultado }
private void btnIgual_Click(object sender, EventArgs e) { FilaLista <string> infixa = new FilaLista <string>(); FilaLista <string> posfixa = new FilaLista <string>(); PilhaLista <string> ops = new PilhaLista <string>(); string expressao = txtVisor.Text; for (int i = 0; i < expressao.Length; i++) { string elemento = ""; if (!IsOp(expressao[i].ToString())) { elemento = ""; int inicial = i; while (inicial + elemento.Length < expressao.Length && (!IsOp(expressao[inicial + elemento.Length].ToString()) || expressao[inicial + elemento.Length] == '.')) { elemento += expressao[inicial + elemento.Length]; } i = inicial + elemento.Length - 1; posfixa.Enfileirar(elemento); } else { elemento = expressao[i] + ""; while (!ops.EstaVazia() && TemPrecedencia(ops.OTopo()[0], elemento[0])) { char op = ops.OTopo()[0]; if (op == '(') { break; } else { posfixa.Enfileirar(op + ""); ops.Desempilhar(); } } if (elemento != ")") { ops.Empilhar(elemento); } else { ops.Desempilhar(); } } if (elemento != "(" && elemento != ")") { infixa.Enfileirar(elemento); } } while (!ops.EstaVazia()) { string op = ops.Desempilhar(); if (op != "(" && op != ")") { posfixa.Enfileirar(op); } } escreverSeq(infixa, posfixa); txtResultado.Text = CalcularResultado(posfixa).ToString(); }
// Acha todos os caminhos usando o algoritmo de backtracking de cada labirinto especificado... public void AcharCaminhos(ref DataGridView dgvLab, ref List <Posicao[]> caminhos, ref int[] qtdPosicoesEmCadaCaminho) //encontra os caminhos { Posicao posAtual = new Posicao(1, 1); //nova posição no início do labirinto Posicao[] vetorPos = new Posicao[labirinto.Matriz.Length]; qtdPosicoesEmCadaCaminho = new int[labirinto.Matriz.Length * 10]; //Garante que não há estouro caminhos = new List <Posicao[]>(); Posicao proxPosicao = null; bool temCaminho; bool achouSaida = false; int qtdPosicoes = 0, qtdCaminhos = 0; Pintar(ref dgvLab, posAtual.Linha, posAtual.Coluna); while (true) { while (true) //loop eterno { proxPosicao = (Posicao)posAtual.Clone(); temCaminho = TemCaminho(ref posAtual, ref proxPosicao); //verifica se tem caminho // Sinaliza no labirinto da classe Labirinto e no labirinto visual (dgvLab) para qual lugar prosseguiu // o cursor depois de usar a Rosa dos Ventos (método TemCaminho()). if (temCaminho) { proxPosicao.OndeParou = -1; pilha.Empilhar(posAtual); posAtual = (Posicao)proxPosicao.Clone(); // Verifica-se se o lugar para onde o cursor foi é a saída ou não. if ((char)dgvLab[posAtual.Coluna, posAtual.Linha].Value != SAIDA) { dgvLab[posAtual.Coluna, posAtual.Linha].Value = JA_PASSOU; this.labirinto.Matriz[posAtual.Linha, posAtual.Coluna] = JA_PASSOU; Pintar(ref dgvLab, posAtual.Linha, posAtual.Coluna); } else { Pintar(ref dgvLab, posAtual.Linha, posAtual.Coluna); if (listaCaminhos.Count == 0) { System.Threading.Thread.Sleep(500); } achouSaida = true; break; } } // Volta a posição anterior - pois não há mais lugares para ir da posição atual, a não ser voltar! else { if (pilha.EstaVazia) { Pintar(ref dgvLab, 1, 1); break; //Não há caminhos } proxPosicao = (Posicao)pilha.OTopo().Clone(); dgvLab[posAtual.Coluna, posAtual.Linha].Value = VAZIO; this.labirinto.Matriz[posAtual.Linha, posAtual.Coluna] = VAZIO; Pintar(ref dgvLab, proxPosicao.Linha, proxPosicao.Coluna); posAtual = (Posicao)pilha.Desempilhar().Clone(); } } // Quando a saída, no labirinto: "S", é achada pelo algoritmo e o caminho feito para chegar até a saída // é adicionado a ArrayList de strings "listaCaminhos", que será usada posteriormente no método "MostrarCaminhos". if (achouSaida) { string ret = ""; int linhaAtual, colunaAtual; PilhaLista <Posicao> pilhaClonada = pilha.Copia(); while (!pilhaClonada.EstaVazia) { linhaAtual = pilhaClonada.OTopo().Linha; colunaAtual = pilhaClonada.OTopo().Coluna; Posicao posicaoAtual = new Posicao(linhaAtual, colunaAtual); vetorPos[qtdPosicoes] = posicaoAtual; ret += $"Linha: {linhaAtual}, Coluna: {colunaAtual}|"; pilhaClonada.Desempilhar(); qtdPosicoes++; } qtdPosicoesEmCadaCaminho[qtdCaminhos] = qtdPosicoes; caminhos.Add(vetorPos); listaCaminhos.Add(ret); // Reseta-se todas as variáveis usadas para encontrarmos um caminho diferente do já encontrado! qtdPosicoes = 0; vetorPos = new Posicao[labirinto.Matriz.Length]; achouSaida = false; } else { if (listaCaminhos.Count > 0) { break; //Encontrou todos os caminhos } else { listaCaminhos.Add("Não há caminhos"); } } if (pilha.EstaVazia) { break; } posAtual = (Posicao)pilha.Desempilhar().Clone(); qtdCaminhos++; } }