Ir para o conteúdo
  • Revista PROGRAMAR: Já está disponível a edição #60 da revista programar. Faz já o download aqui!

fo_11

Duvida no retorno

Mensagens Recomendadas

fo_11

As minhas duvidas estão assinaladas no programa:

OBS:Coloquei o programa completo para em caso de conflitos poderem descubrir de onde surgiram.

#include<stdio.h>
#include<stdlib.h>
#include<string.h>

typedef struct{
                  long int bi;
                  char *nome;
                  int idade;
                  int salario;
                  char sexo;
              }PESSOA;


PESSOA* registar(int*);
int main()
{
    PESSOA *id=NULL;//é necessario igual o id a null
    int n_pessoas;
    id=registar(&n_pessoas);//esta parte está correcta? o id irá irá ocupar a memoria necessaria para receber este retorno?
    
    free(id);//neste caso é necessario o free?
    system("pause");
}

PESSOA* registar(int *n_pessoa)
{
        PESSOA *id=NULL;
        int bi;
        char nome[50];
        *n_pessoa=0;
        
        do
         {printf("==========%d PESSOA========\n\n",*n_pessoa+1);
          printf("Insira bi==>");scanf("%d",&bi);
          
          if(bi>0)
           {rewind(stdin);//limpar buffer teclado devido ao uso do gets
            id=(PESSOA*)realloc(id,(++(*n_pessoa))*sizeof(PESSOA));
            printf("Insira nome==>");gets(nome);
            printf("Insira idade==>");scanf("%d",&id[*n_pessoa-1].idade);
            printf("Insira salario==>");scanf("%d",&id[*n_pessoa-1].salario);
            printf("Insira sexo==>");scanf(" %c",&id[*n_pessoa-1].sexo);
            
            id[*n_pessoa-1].bi=bi;
            id[*n_pessoa-1].nome=(char*)malloc(strlen(nome)*sizeof(char));
            strcpy(id[*n_pessoa-1].nome,nome);
           }
         }while(bi>0);
        
         return id;
         free(id);
}
            
       

Partilhar esta mensagem


Ligação para a mensagem
Partilhar noutros sites
Localhost

Não percebi bem se era uma pergunta ou não (o 1º comentário), de qualquer das formas, sim é necessário inicializar com NULL, neste caso até nem era porque logo a seguir vais receber um endereço mas é sempre uma boa prática.

Quanto à 2º pergunta, o id é do mesmo tipo que o retorno, portanto, sim o id vai poder receber o retorno sem problemas.

Quanto à 3º pergunta, é necessário o free porque se reparares o id nessa altura já recebeu o endereço de uma estrutura que está alocada dinamicamente. Ela como foi alocada dinamicamente vai permanecer até o final da execução do programa, ou seja, se tu já tens o endereço já podes libertar essa memória para não existir nenhum leak. Na verdade, acho que o teu SO iria repôr tudo normalmente mas fazer free é sempre um boa prática porque quando estás com programas muito maiores, como um jogo por exemplo, em que tens muita memória ocupada se não fizeres free vais acabar por desperdiçar memória e who knows, heap overflow mas isto é uma suposição.

Tenho agora só mais umas notas. Não percebi aquele rewind, o problema da função gets está em não checar limites. Podes até estar correcto mas eu pessoalmente acho isso muito esquisito. Estará aqui alguém para me corrigir.

Para finalizar, tu não precisavas de fazer return da estrutura. Passavas para a função o endereço da mesma e depois alteravas os seus campos com o operador ->.

typedef struct {
  int devil;
}blah;

int main(void) {
  blah rofl;
  modify(&rofl);
}

void modify(blah *rofl) {
  rofl -> devil = 666;
}

Tipo isto.  :)


here since 2009

Partilhar esta mensagem


Ligação para a mensagem
Partilhar noutros sites
fo_11

Se não fizer rewind devido à utilização do scanf em cima o gets (que deveria ser fgets  :)) não funciona, isto é, e pelo que li por ai fica com o '\n' introduzido por nos no momento do enter.

Partilhar esta mensagem


Ligação para a mensagem
Partilhar noutros sites
Localhost

Pensei que estavas a fazer rewind porque pensavas que assim a utilização da função gets já não era perigosa.

Ficaram esclarecidas as outras dúvidas?


here since 2009

Partilhar esta mensagem


Ligação para a mensagem
Partilhar noutros sites
fo_11

Sim ficaram. Obrigado.

Só mais uma questão que já é fora de tópico.

Eu estou a fazer estes programas para me preparar para fazer um trabalho em c para a faculdade, e o que tenho verificado é que os códigos já estão a ficar grandes o suficiente para me conseguirem desorentar. E o que tenho feito é dividir partes indepentes do programa,  em programas mais pequenos.

O problema encontra-se quando eu quero trabalhar com o programa tenho de estar sempre andar de um lado para o outro para fazer o que o programa faz (lembrar que o programa como ele todo são varios programas de menores dimensoes). Será muito complicado juntá-los tipo num programa de uma especie main (principal, quero eu dizer, corro aquele programa e ele proprio vai buscar as informações necessarias aos outros programas) e os outros serem transformados numa especie de biblioteca?

Partilhar esta mensagem


Ligação para a mensagem
Partilhar noutros sites
Localhost

Podes criar um resource file (*.h). Lá podes declarar variáveis, protótipos de funções, etc.

Depois no teu *.c incluis esse resource file.

#include "blah.h"


here since 2009

Partilhar esta mensagem


Ligação para a mensagem
Partilhar noutros sites
fo_11

Basicamente trabalho dois programas independetes sem me preocupar que vou junta-los, onde quero chegar é, faço includes das bibliotecas normalmente, crio estruturas, variaveis tudo na mesma para os dois. No final num deles faço include do outro e já está?

Partilhar esta mensagem


Ligação para a mensagem
Partilhar noutros sites
Localhost

Atenção, não podes desenvolver funções dentro dos resources files. Só podes declarar as variáveis, etc.

No final podes incluir nos teus dois programas e já podes utilizar essas variáveis que declaraste.


here since 2009

Partilhar esta mensagem


Ligação para a mensagem
Partilhar noutros sites
fo_11

Surgiu uma outra duvida relacionada com a memoria dinamica.

Quando temo int *f=NULL; e por alguma razao nunca a chegamos a utilizar (está abaixo de um menu e por vezes saimos daquela função sem fazer uso dela); é necessario o free(f)?

Partilhar esta mensagem


Ligação para a mensagem
Partilhar noutros sites
Localhost

Não metas. Tu só fazes free se tiveres memória alocada, se não tiveres vais estar a fazer free a quê, a NULL?

Eu acho que uma vez eu fiz isso e o meu programa crashou mas eu estou em Linux, pode ser diferente.


here since 2009

Partilhar esta mensagem


Ligação para a mensagem
Partilhar noutros sites

Crie uma conta ou ligue-se para comentar

Só membros podem comentar

Criar nova conta

Registe para ter uma conta na nossa comunidade. É fácil!

Registar nova conta

Entra

Já tem conta? Inicie sessão aqui.

Entrar Agora

×

Aviso Sobre Cookies

Ao usar este site você aceita os nossos Termos de Uso e Política de Privacidade. Este site usa cookies para disponibilizar funcionalidades personalizadas. Para mais informações visite esta página.