Pilhas (Funções Criar)


Página 1 de 3    1  2 3 
22-04-2006 por palominha
Pilhas (Funções Criar)
Oi pessoal, comecei a estudar pilhas e aí vão algumas dúvidas pra que possam me ajudar:

Esse exemplo é do livro pelo qual estou estudando, mas ñ entendi muito bem.

Pirmeiro criar uma struct composta de vetores
Código:
#define N 50 struct pilha{ int n float vet[N]; };

Função para criar uma pilha, o conceito do livro é para criar uma pilha aloca-se dinamicamente esse estrutura e inicializa a pilha como sendo vazia, isto é, como numero de elemento iguais a zero,aí começam as dúvidas:

Código:
Pilha* pilha_cria(void) { Pilha* pilha=(Pilha*)malloc(sizeof(Pilha)); p->n=0; retunr p; }
1 - Porque ele cria um ponteiro Pilha que aponta para a função e não um para a struct, para o qual esse ponteiro deveria apontar, e como ele tem acesso aos dados da struct?

2 - O conceito fala que aloca para a struct e na minha visão isso ñ acontece, pq a struct chama-se pilha e ele aloca para Pilha.
22-04-2006 por Rui_Carlos
1) "...um ponteiro pilha que aponta para a função...", não percebi, não vejo nenhum ponteiro apontadando para uma função!!!

de qualquer modo você tem que alocacar dinâmicamente a struct porque caso contrário ela é destruída quando a função terminar.
22-04-2006 por palominha
Citação:
Postado Originalmente por Rui_Carlos
1) "...um ponteiro pilha que aponta para a função...", não percebi, não vejo nenhum ponteiro apontada para uma função...
Código:
Pilha* pilha_cria(void)
Essa linha acima não quer dizer isso Pillha*(ponteiro) aponta para a função pilha_cria ops:

Mas esse código pelo que vejo ñ está alocando para a struct ñ é, ou estou errada :cry:
Código:
Pilha* pilha_cria(void) { Pilha* pilha=(Pilha*)malloc(sizeof(Pilha)); p->n=0; retunr p; }
22-04-2006 por Rui_Carlos
'Pilha* pilha_cria(void)' significa que a função 'pilha_cria' devolve um apontador para 'Pilha' (devolve 'Pilha*')

Código:
Pilha* pilha=(Pilha*)malloc(sizeof(Pilha));
nesta linha estamos a alocar espaço para uma 'Pilha'; a função devolve um apontador para o local onde foi reservada a memória para a pilha.
22-04-2006 por palominha
Apontador
Desculpa mas agora é que não entendi nada mesmo ops:

APONTADOR :?:
22-04-2006 por Rui_Carlos
ponteiro=apontador (em português)
22-04-2006 por palominha
Devolvendo um Ponteiro
Olha só eu ñ estou entendendo o sentido disso, pq a função devolve um ponteiro e não é um ponteiro para Pilha :roll:
22-04-2006 por Rui_Carlos
o código tem algumas incorrecções, uma (possível) forma correcta seria
Código:
typedef struct pilha { int n; float vet[N]; }Pilha; Pilha* pilha_cria(void) { Pilha* p=(Pilha*)malloc(sizeof(Pilha)); //é alocado espaço para uma pilha p->n=0; //é inicializada a pilha return p; //o retornado o "local" onde está a pilha (ou seja o ponteiro para a pilha) }
22-04-2006 por palominha
Código Incorreto
Poxa então o livro está errado :x

Outra coisa, o código abaixo
Código:
Pilha* pilha_cria(void) { Pilha* p=(Pilha*)malloc(sizeof(Pilha)); p->n=0; return p; }
É a mesma coisa de:
Código:
Pilha *pilha_cria(void) { Pilha *p; p=(Pilha*)malloc(sizeof(Pilha)); p->n=0; return p;
22-04-2006 por Rui_Carlos
assim à primeira vista, sim, os dois códigos são equivalentes...

quanto ao livro estar errado, embora eu não tenha testado o código que você colocou eu aposto que ele não vai correr...
...embora os erros seja apenas pequenos pormenores, pois o código que eu postei é quase igual ao seu.

(adicionais uns comentários ao código do meu post anterior...)
22-04-2006 por palominha
Pilhas (Função Incluir)
Bom agora que eu já entendi a função criar, aí vão algumas dúvidas sobre a função inlcuir(empilhar)

Conceito do livro: Usamos a próxima posição livre do vetor, devemos ainda assegurar que existe espaço para a inserção do novo elemento, tendo em vista que se trata de um vetor de dimensão fixa.
Código:
void pilha_push(Pilha* p, float v) { if(p->n==N){ printf("Capacidade da pilha esgotada.\n"); exit(1); } p->vet[p->n]=v; p->n++; }
Minhas dúvidas são:

1 - A função passa como parâmetro Pilha* p, mas pelo jeito o correto seria pilha* p, estou certa?
2 - Não entendi pq?
Código:
p->vet[p->n]=v p->n++
22-04-2006 por Rui_Carlos
questão 1
depende de qual a definição da struct com que você está a trabalhar:
para esta versão (a que eu utilizaria)
Código:
typedef struct pilha { int n; float vet[N]; }Pilha;
seria 'Pilha* p'

para
Código:
struct pilha{ int n float vet[N]; };
seria 'struct pilha* p'

nunca poderia ser apenas 'pilha* p'

questão 2
em 'p->n' temos a próxima posição do vector livre (inicialmente é a posição 0), logo, quando adicionamos um elemento, ele será inserido na posição 'p->n' (ou seja 'p->vet[p->n]').
depois, como inserimos um elemento, a próxima posição livre passa a ser a imediatamente a seguir à actual (ou seja, temos que fazer 'p->n++').
22-04-2006 por jackinabox
Re: Pilhas (Função Incluir)
Citação:
Postado Originalmente por palominha
A função passa como parâmetro Pilha* p
... "passa", não. Recebe como parâmetro.

Bem, trabalhar com estruturas de dados requer meticulosidade e domínio da sintaxe da linguagem de programação e entendimento dos algoritmos.

É bem difícil aprender se você não observar cada detalhe, cada linha.

Sem esses requisitos, pode ficar difícil entender coisas (que na realidade são simples) como
Código:
p->vet[p->n]=v; p->n++;
Lembro do tempo em que eu costumava estudar estruturas de dados. Se eu não desenhasse em um papel o que estava acontecendo passo a passo, acompanhando a alocação de memória, o conteúdo das variáveis, etc., eu nunca conseguia entender o que estava acontecendo, nem o porquê.

Lembro das minhas primeiras aulas de algoritmos (com professor horrível), em que eu queria desistir de estudar Ciências de Computação.
Lembro das horas e horas que eu ficava tentando entender os tais ponteiros, e quando eu achava que tinha entendido, notava que eu não sabia era nada.

Citação:
1 - Porque ele cria um ponteiro Pilha que aponta para a função e não um para a struct, para o qual esse ponteiro deveria apontar, e como ele tem acesso aos dados da struct?
Veja só: consulte a definição da função malloc(). Entenda que malloc() retorna um ponteiro (apontador) para a área de memória alocada. E é nessa área de memória alocada que será armazenada a pilha. Desenhe a área de memória alocada, desenhe um ponteiro que aponta para essa área, que é onde será inicializada uma Pilha, então escreva nessa área os campos da struct.

E não esqueça que a declaração da pilha não é uma variável. Aqui nesse lugar onde está escrito
Código:
struct Pilha { int n; float vet[N]; }
existe apenas uma declaração de um tipo (no caso, uma struct) chamado "Pilha". Não existe aqui uma instância de uma pilha. Nessas linhas de código acima, não está sendo alocada pilha nenhuma, o código diz apenas "uma Pilha é uma estrutura (struct) composta por um int chamado n e por um array de float chamado vet". Mas somente haverá uma pilha em memória quando for declarada uma variável do tipo struct Pilha (ou quando for alocada memória dinamicamente para armazená-la, que é o caso desse exemplo) e quando essa área de memória for devidamente inicializada.
24-04-2006 por palominha
Pilhas (Funções Crias e Incluir)
Eu fiz as funções criar e incluir diferente das do livro, mas está dando um erro no exit(1), alguém pode me dar uma ajuda e também verificar se dessa forma está legal.

Código:
#include <stdio.h> #include <stdlib.h> #define N 50 typedef struct Pilha{ int n; int vet[N]; }TPilha; TPilha *pilha_cria() { TPilha *p; p=(TPilha*)malloc(sizeof(TPilha)); p->n=0; return (p); } TPilha *pilha_push(int v) { pilha_cria();//chamando a função TPilha *p; if(p->n==N){ printf ("Capacidade da pilha esgotada.\n"); exit (1); } p->vet[p->n]=v; p->n++; }
24-04-2006 por peczenyj
Acho que vc deveria fazer algo assim:

Código:
TPilha *p; p = (TPilha *) pilha_cria();

Porém eu gostaria de entender por que vc está usando malloc nesse caso. Eu acho que Pilha é uma só, vc teria que alocar o vetor vet, mas vc ja aloca um espaço (50) para ele...

Da uma olhada nesses exemplos:

http://www.java2s.com/Code/C/Data-Structure-Algorithm/StackinC.htm
http://www.java2s.com/Code/C/Data-Structure-Algorithm/Asimplefourfunctioncalculator.htm
24-04-2006 por palominha
Pilhas (Funções Crias e Incluir)
Citação:
Postado Originalmente por peczenyj
Acho que vc deveria fazer algo assim:

[code] TPilha *p;
p = (TPilha *) pilha_cria();...
O que quer dizer o código acima, estou alocando um espaço para 50 elementos que devem ser armazenados na pilha, pq pelo livro que estou estudando o conceito é de que seja comum conhecer de antemão o número máximo de elementos que podem ser armazenados.
24-04-2006 por Rui_Carlos
Citação:
Postado Originalmente por peczenyj
Acho que vc deveria fazer algo assim:

Código:
TPilha *p; p = (TPilha *) pilha_cria();
para quê o casting?


palominha a sua função 'push' não faz muito sentido...

... o objectivo dessa função é inserir um novo elemento na stack, certo?
mas sempre que você executa a função você está a criar uma nova stack, ou seja você só vai ter stacks com um elemento !!!

na minha opinião a função push devia ser algo do género:
Código:
TPilha* pilha_push(TPilha* p,int v) { if(p->n==N) { printf("...."); exit(1); } p->vect[p->n]=v; p->n++; return p; }
ou seja, você insere um elemento numa stack recebida como argumento.
24-04-2006 por palominha
Pilhas (Funções Crias e Incluir)
Então quer dizer que isto que estou fazendo é criar uma nova pilha e ñ inserir um novo elemento na mesma ops:

Então vamos linha a linha pra eu poder entender :roll:

Aqui eu aponto a função para a struct e passo como parâmetro uma variável que irá receber o valor
Código:
TPilha *pilha_push(int v)
Aqui eu chamo a função da pilha que criei
Código:
pilha_cria();
Aqui eu crio uma variável do tipo ponteiro para a struct
Código:
TPilha *p;
Aqui eu verifico a capacidade da pilha
Código:
if(p->n==N){ printf ("Capacidade da pilha esgotada.\n"); exit (1); }
Aqui eu estou inserindo os elementos (pelo eu penso que seja assim)
Código:
p->vet[p->n]=v; p->n++;
24-04-2006 por Rui_Carlos
Re: Pilhas (Funções Crias e Incluir)
Citação:
Postado Originalmente por palominha
Então quer dizer que isto que estou fazendo é criar uma nova pilha e ñ inserir um novo elemento na mesma ops:
não foi isso que eu disse...

você está a inserir o elemento efectivamente, mas normalmente o que nós queremos é criar uma stack, depois inserir um elemento, depois inserir outro, etc. e isto a sua função não permite; a sua função apenas permite ter stacks com um elemento...

normalmente as funções que criam e que inserem elementos são "independentes". nós temos uma função que cria uma stack e outra que insere um elemento numa stack já criada (e eventualmente outras para remover, consultar, etc.)

e outro pormenor, você está esquecendo retornar a pilha na função 'pilha_push'.
24-04-2006 por Rui_Carlos
Citação:
Postado Originalmente por palominha
Aqui eu chamo a função da pilha que criei ...
não, aqui você chama uma função para criar uma nova pilha.

é precisamente por isso que a sua função não faz sentido, você está a criar uma nova pilha de cada vez que insere um elemento...
 
Guia do Hardware Melhores Tópicos