#Makefile para compilar todos los modulos

all: primers llistat.o: llistat.c llistat.h gcc - c llistat.c primers.o:llistat
.o primers.c gcc - c primers.c primers:llistat.o pr
    imers.o gcc primers.o llistat.o - o primers
/****************************llistat.c**************************/
#include "llistat.h"

llistat LLISTAT_Crea()
{
	//funcion que inicializa la estructura LLISTAT
	llistat ll;

	ll.pri = NULL;
	ll.pdi = NULL;
	ll.ult = NULL;

	return ll;
}

llistat LLISTAT_Insereix(llistat ll, int num)
{
	//funcion que annade un numero al final del listado

	node *aux;
	//definimos el puntero a la nueva estructura


	aux = (node *) malloc(sizeof(node));
	//pedimos memoria para la estructura

	if (aux != NULL) {
		aux->num = num;
		//ponemos en el campo num el numero a annadir


		aux->ps = NULL;
		//como annadimos siempre al final, hacemos que no
		//apunte en ningun sitio

		if (ll.pri == NULL) {
			//tenemos de actuar diferente si es el primer numero
			//que annadimos o no lo es

			ll.pri = aux;
			ll.ult = aux;
			ll.pdi = aux;
			//y todos los punteros al unico numero

		} else {
			ll.ult->ps = aux;
			//el que era ultimo, hacemos que apunte al nuevo
			//ultimo

			ll.ult = aux;
			//y el puntero a ultimo que apunte al nuevo 
			//ultimo
		}
	} else {
		printf("Error pidiendo memoria\n");
		exit(0);
	}
	return ll;
	//devolvemos la lista nueva modificada
}

int LLISTAT_Consulta(llistat ll)
{
	return (ll.pdi->num);
	//devolvemos el numero apuntado por pdi
}

int LLISTAT_esFi(llistat ll)
{
	return (ll.pdi->ps == NULL);
	//estamos en el ultimo numero si el puntero a siguiente 
	//no apunta a ningun sitio
}


llistat LLISTAT_VesAlPrincipi(llistat ll)
{
	ll.pdi = ll.pri;
	//hacemos que "punto de interes" sea el principio
}

llistat LLISTAT_Avanca(llistat ll)
{
	ll.pdi = ll.pdi->ps;
	//avanzamos uno, si podemos -si estamos al final ll.pdi
	//apuntara a NULL!! -> un poco incorrecto
	return ll;
}
/*********************************llistat.h**********************/
#ifndef LLI_
#define LLI_

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

struct node_ {
	int num;
	struct node_ *ps;
};

typedef struct node_ node;
//hacemos estructura node

typedef struct {
	node *pri;
	node *pdi;
	node *ult;
} llistat;
//y tendremos como un listado para guardar los numeros  

llistat LLISTAT_Crea();
llistat LLISTAT_Insereix(llistat ll, int num);
llistat LLISTAT_VesAlPrincipi(llistat ll);
llistat LLISTAT_Avanca(llistat ll);
int LLISTAT_Consulta(llistat ll);

int LLISTAT_esFi(llistat ll);
void LLISTAT_Destrueix(llistat ll);

#endif
/********************************primers.c************************/
#include "llistat.h"

int esPrimer(int c, llistat ll);

int main()
{

	int comprova;
	llistat ll;

	ll = LLISTAT_Crea();
	//iniciamos la lista

	ll = LLISTAT_Insereix(ll, 2);
	//inserimos el numero 2

	ll = LLISTAT_VesAlPrincipi(ll);
	//vamos al principio

	printf("2-");
	//escrivimos el 2 en pantalla

	comprova = 3;
	//empezamos a atacar con el numero 3

	while (comprova < 2000000) {
		//mientras estemos comprobando numeros menores de 2000000
		//seguimos comprobando

		if (esPrimer(comprova, ll)) {
			//si el numero ha sido primero, lo escrivimos
			//en pantalla y lo annadimos en la lista
			printf("%d-", comprova);
			ll = LLISTAT_Insereix(ll, comprova);
		}

		comprova = comprova + 2;
		//avanzamos dos, asi nos saltamos los numeros pares
	}
	return 1;
}

int esPrimer(int c, llistat ll)
{

	//esta funcion nos devuelve 1 si el numero es primero y 0
	//si no lo es

	int ret;
	ret = 1;
	//suponemos que es primero, si conseguimos demostrar que no lo
	//es pues ya devolveremos 0
	ll = LLISTAT_VesAlPrincipi(ll);
	//vamos al principio para hacer las comprobaciones

	while (ret && !LLISTAT_esFi(ll)
	       && LLISTAT_Consulta(ll) * LLISTAT_Consulta(ll) <= c + 1) {
		/*Seguiremos comprobando mientras:
		   -sea primero (si no lo es devolvemos que no loes)
		   -no lleguemos al final del listado (precindible seguramente
		   con la siguiente condicion)
		   -estemos comprobando numeros menores de la raiz cuadrada
		   del numero que estemos atacando
		 */
		if (c % LLISTAT_Consulta(ll) == 0) {
			ret = 0;
			//si la division da exacto, no es primero!
		} else {
			ll = LLISTAT_Avanca(ll);
			//no ha sido primero, avanzamos en la lista
			//(tambien podriamos hacerlo fuera del else)
		}
	}
	return ret;
	//devolvemos la verdad sobre el numero

}