public Vertice[] GetAdjacentes() { Elemento aux = Arestas.pri.Prox; Vertice[] adj = new Vertice[Arestas.Tamanho]; int pos = 0; while (aux != null) { Aresta auxA = (Aresta)aux.Dados; if (auxA.Origem.Nome == nome && adj.Contains(auxA.Destino) == false) { adj[pos] = auxA.Destino; pos++; aux = aux.Prox; } else if (auxA.Destino.Nome == nome && adj.Contains(auxA.Origem) == false) { adj[pos] = auxA.Origem; pos++; aux = aux.Prox; } else { aux = aux.Prox; } } return(adj); }
/// <summary> /// Conta a quantidade de arestas que tem como origem o vértice informado por parâmetro /// </summary> /// <param name="v1">vértice informado pelo usuário</param> /// <returns> /// Grau de saída do vértice informado /// </returns> public int GetGrauSaida(Vertice v1) { int grauSaida = 0; Elemento aux = v1.Arestas.pri.Prox; //busca o primeiro elemento da lista de arestas do vértice informado por parâmetro while (aux != null) { Aresta auxA = (Aresta)aux.Dados; if (auxA.Origem.Equals(v1)) //se o vertice de origem da aresta atual é igual ao vertice informado { grauSaida++; //aumenta o valor do grau de saída do vertice a ser retornado aux = aux.Prox; } else { aux = aux.Prox; //parte para o proximo elemento } } return(grauSaida); }
/// <summary> /// Um grafo complementar é um grafo resultante de outro grafo, um grafo complementar possui vértices e arestas necessárias para tornar um grafo completo /// </summary> /// <returns>Um grafo complementar</returns> public GNaoDirigido GetComplementar() { GNaoDirigido Gcomplementar; ListaVertice verticesAux = new ListaVertice(); ListaAresta arestasAux = new ListaAresta(); if (IsCompleto()) { return(this); } else { int pos = 0; Vertice[] aux = vertices.GeraVetor(); while (pos < aux.Length) { for (int i = 0; i < aux.Length - 1; i++) { if (!IsAdjacente(aux[pos], aux[i + 1]))// Comparando os vértices e verificando se há adjacência entre eles { Vertice clone = new Vertice(aux[pos].Nome); Vertice clone2 = new Vertice(aux[i + 1].Nome); if (verticesAux.BuscarVertice(clone) != null) { clone = (Vertice)verticesAux.Buscar(clone); } if (verticesAux.BuscarVertice(clone2) != null) { clone2 = (Vertice)verticesAux.Buscar(clone2); } Aresta auxA = new Aresta(clone, clone2, 0); arestasAux.Adicionar(auxA); if (verticesAux.BuscarVertice(clone) == null) { verticesAux.Adicionar(clone); } clone.Arestas.Adicionar(auxA); if (verticesAux.BuscarVertice(clone2) == null) { verticesAux.Adicionar(clone2); } clone2.Arestas.Adicionar(auxA); vertices.BuscarVertice(clone).Arestas.Adicionar(auxA); vertices.BuscarVertice(clone2).Arestas.Adicionar(auxA); } } pos++; } Gcomplementar = new GNaoDirigido(verticesAux, arestasAux); return(Gcomplementar); } }
/// <summary> /// Método para gerar o grafo /// </summary> /// <param name="caminho">o arquivo que o usuário informa</param> /// <returns>Retorna um grafo</returns> protected Grafo GeraGrafo(Stream caminho) { Grafo g; ListaVertice vertices = new ListaVertice(); ListaAresta arestas = new ListaAresta(); string arquivo = LeitorArquivo.LerArquivo(caminho); //As linhas do arquivos sem tratamento string[] infoGrafo = LeitorArquivo.FormatarArquivo(arquivo); // Vetor com o arquivo tratado string[] linhasArquivo = arquivo.Replace("\r", "").Split('\n'); //Vetor com as linhas do arquivo (utilizada no for para gerar o grafo) this.IsDigrafo(arquivo); //é orientado if (digrafo) { g = new GDirigido(); vertices.GerarLista(int.Parse(infoGrafo[0])); for (int i = 1; i < infoGrafo.Length; i = i + 4) { //Lista de arestas Aresta auxA; if (int.Parse(infoGrafo[i + 3]) == 1) //Se a aresta tem direção 1, cria a aresta com origem e destino na sequencia informada { Vertice auxVo = vertices.BuscarVertice(new Vertice(Convert.ToInt32(infoGrafo[i]))); Vertice auxVd = vertices.BuscarVertice(new Vertice(Convert.ToInt32(infoGrafo[i + 1]))); auxA = new Aresta(auxVo, auxVd, int.Parse(infoGrafo[i + 2])); arestas.Adicionar(auxA); } else //se não, cria a aresta com origem e destino na direção inversa { Vertice auxVo = vertices.BuscarVertice(new Vertice(Convert.ToInt32(infoGrafo[i + 1]))); Vertice auxVd = vertices.BuscarVertice(new Vertice(Convert.ToInt32(infoGrafo[i]))); auxA = new Aresta(auxVo, auxVd, int.Parse(infoGrafo[i + 2])); arestas.Adicionar(auxA); } if (vertices.Buscar(auxA.Origem) == null) { vertices.Adicionar(auxA.Origem); vertices.BuscarAdicionarOrigem(auxA); } else { vertices.BuscarVertice(auxA.Origem).Arestas.Adicionar(auxA); } if (vertices.Buscar(auxA.Destino) == null) { vertices.Adicionar(auxA.Destino); vertices.BuscarAdicionarDestino(auxA); } else { vertices.BuscarVertice(auxA.Destino).Arestas.Adicionar(auxA); } } return(g = new GDirigido(vertices, arestas, digrafo)); } else //Não é orientado { g = new GNaoDirigido(); try { vertices.GerarLista(int.Parse(infoGrafo[0])); for (int i = 1; i < infoGrafo.Length; i = i + 3) { //Lista de arestas Vertice auxVo = vertices.BuscarVertice(new Vertice(Convert.ToInt32(infoGrafo[i]))); Vertice auxVd = vertices.BuscarVertice(new Vertice(Convert.ToInt32(infoGrafo[i + 1]))); Aresta auxA = new Aresta(auxVo, auxVd, int.Parse(infoGrafo[i + 2])); arestas.Adicionar(auxA); if (vertices.Buscar(auxA.Origem) == null) { vertices.Adicionar(auxA.Origem); vertices.BuscarAdicionarOrigem(auxA); } else { vertices.BuscarVertice(auxA.Origem).Arestas.Adicionar(auxA); } if (vertices.Buscar(auxA.Destino) == null) { vertices.Adicionar(auxA.Destino); vertices.BuscarAdicionarDestino(auxA); } else { vertices.BuscarVertice(auxA.Destino).Arestas.Adicionar(auxA); } } } catch (Exception) { MessageBox.Show("O arquivo informado está em um formato incorreto", "Erro", MessageBoxButtons.OK, MessageBoxIcon.Error); MessageBox.Show("O arquivo deve seguir esse padrão: (Exemplo)\n3\n1; 2; 7\n1; 3; 3\n2; 3; 10", "Correção", MessageBoxButtons.OK, MessageBoxIcon.Error); return(null); } return(g = new GNaoDirigido(vertices, arestas)); } }
public bool HasCiclo() { Elemento vStart = vertices.pri.Prox; int[] visitados = new int[(vertices.Tamanho - 1)]; int visitaCount = 0; Elemento auxV = vertices.pri.Prox; auxV = vStart; int fimBusca = 0; Vertice auxVx = (Vertice)auxV.Dados; while (fimBusca == 0) { if (GetGrauEntrada(auxVx) != 1) //se o grau de entrada não for 1, significa que não existe um ciclo, pois não existe aresta chegando ao vertice ou existem mais de uma aresta chegando ao vertice { fimBusca = 1; //indica que a busca pelo ciclo terminou break; } else if (GetGrauSaida(auxVx) != 1) //se o grau de saida não for 1, significa que não existe um ciclo, pois não existe aresta saindo do vertice ou existem mais de uma aresta saindo do vertice { fimBusca = 1; //indica que a busca pelo ciclo terminou break; } Elemento AuxAr = auxVx.Arestas.pri.Prox; Aresta auxA = (Aresta)AuxAr.Dados; if (auxA.Origem.Equals(auxVx)) { if (visitados.Contains(auxA.Destino.Nome)) { if ((visitaCount) == visitados.Length && auxA.Destino.Equals((Vertice)vStart.Dados)) { return(true); } else { fimBusca = 1; //indica que a busca pelo ciclo terminou break; } } else { visitados[visitaCount] = auxVx.Nome; visitaCount++; auxVx = auxA.Destino; } } else { auxA = (Aresta)AuxAr.Prox.Dados; if (visitados.Contains(auxA.Destino.Nome)) { if ((visitaCount) == visitados.Length && auxA.Destino.Equals((Vertice)vStart.Dados)) { return(true); } else { fimBusca = 1; //indica que a busca pelo ciclo terminou break; } } else { visitados[visitaCount] = auxVx.Nome; visitaCount++; auxVx = auxA.Destino; } } } if (fimBusca == 1) { return(false); } else { return(true); } }