Elias Granja Jr. Free as in free speech

21Jun/110

Copiando vetores em C

Este semestre tive na faculdade a matéria de estrutura de dados e junto com ela veio a obrigação de implementar algoritmos de ordenação de dados tanto em Java como em C e acabei tendo de resolver o mesmo dilema já explicado neste post.

Para isto resolvi usar o memmove que funciona da seguinte maneira:

memmove( (int*) vetor_destino, (int*) vetor_origem, sizeof(int) * tamanho_do_vetor );

Lembrando que a função pode ser usada para qualquer tipo de ponteiro, então é só trocar o int pelo tipo da váriavel que você está usando.

Tagged as: No Comments
21Mar/110

Lista encadeada genérica em C[Parte 1 de 2]

Afim de evitar ficar usando vetores durante os exercícios da faculdade, decidi criar um header com métodos e uma struct de lista encadeada. Logo de cara percebi que não ia ser uma boa idéia criar structs para cada tipo de dado que poderia um dia usar em sala de aula.

Em C++, java e outras linguagens orientadas a objetos, podemos resolver isso com polimorfismo, sobrecarga de métodos e outras coisinhas muito úteis, mas um tanto distantes do mundo C.

Assim,  depois de alguma pesquisa descobri a existência do ponteiro void, que pode apontar para qualquer tipo de variável, contanto que você faça casting antes de usa-lá, como é possível ver neste exemplo.

Tudo muito bonito, mas ainda seria necessário saber o tipo da variável para fazer o casting antes de compara-las numa função para procurar um valor na lista, por exemplo. Ou seja, consigo criar apenas uma struct, porém as dezenas de métodos repetidos para os principais tipos de dados continua existindo.

Porém, existe outra função bem legal no gcc que se chama typeof, sua sintaxe se parece muito com o typedef:

int inteiro;
typeof(inteiro) novoInteiro;

Agora sim me livrei das dezenas de funções, né? Bom, infelizmente não. Ao colocar o ponteiro diretamente como em:

void *inteiro;
int t = 0;
inteiro = &t;
typeof(*inteiro) novoInteiro;

Ou ainda:

void *inteiro;
int t = 0;
inteiro = &t;
typeof(inteiro) novoInteiro;

O resultado obtido nunca era o esperado(do "novoInteiro" se tornar realmente um inteiro).

Dessa vez, fui pedir ajuda para saber se teria alguma forma de fazer alguma combinação de typeof e void * para eliminar funções extras. O Andrei Formiga deu a ideia de guardar em cada nó um inteiro com o tamanho do dado  que void * aponta, assim poderia utilizar o typeof com este valor e ter a minha tão sonhada variável "genérica".

Basicamente:

void variavel(void *gen){
  int tamanho = sizeof(*gen);
  typeof(tamanho) variavelGenerica;
}

E assim, um nerd conseguiu criar sua tão sonhada lista encadeada genérica em C. No próximo post disponibilizo o código e detalho o que fiz.