Je travaille sur un projet et je crée ici des structures de joueurs qui vont pouvoir etre modifiables (argent, position ect) sauf que ici j'ai un probleme, quand je fais un test dans mon main pour voir ce qui ressort de mon sous-prog creation_structures_joueurs et il me renvoie un nombre tres grand dans la console... pour l'argent...
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
typedef struct joueur
{
char pseudo;
int argent;
int position;
}t_joueur;
int nb_player()
{
// demannde le nombre de joueurs
int nb_joueurs = 1;
while (nb_joueurs != 2 && nb_joueurs != 3 && nb_joueurs != 4)
{
printf("A combien souhaitez-vous jouer ?\n");
scanf("%d", &nb_joueurs);
}
return nb_joueurs;
}
int creation_structures_joueurs()
{
int nombre_joueurs = nb_player();
t_joueur joueur_x[nombre_joueurs];
for (int x = 0; x < nombre_joueurs; x++)
{
printf("Joueur %d, entrez votre pseudo : ", x+1);
fflush(stdin);
gets(&joueur_x[x].pseudo);
joueur_x[x].argent = 1500;
joueur_x[x].position = 0;
}
}
int main()
{
int x = 0;
t_joueur joueur_x[x];
creation_structures_joueurs();
printf("Le joueur %d a %d$ !", x+1, joueur_x[x].argent);
return 0;
}
Ça commence pas très bien : dans ta fonction main tu crées un tableau joueur_x de taille 0. tu ne va donc pas pouvoir y mettre grand chose !
Ta fonction creation_structures_joueurs ne modifie en rien ce tableau (Elle a son propre tableau joueur_x qui n'a rien à voir avec celui là.
Et tu affiches le champ argent de la 1ere case du tableau de la fonction main. case qui n'existe pas puisqu'il en a 0 de case, ça affiche donc n'importe quoi et ça aurait très bien pu planter.
Pour modifier un tableau dans une fonction, le plus simple est de le passer en argument de cette fonction. Le tableau sera alors modifié, pas besoin de le renvoyer par un 'return'.
Ok mais du coup j'ai une question : comment renvoyer les tableaux joueur_x[x] ?
Voilà une phrase qui montre ta mécompréhension. Il n'y a qu'un seul tableau et c'est joueur_x. Il contient x éléments et pour y accéder tu utiliseras joueur_x[0], joueur_x[1], …, joueur_x[x-1]. joueur_x[x] est un élément qui sera toujours en dehors du tableau et pourra provoquer des erreurs …
Le prototype de ta fonction creation_structures_joueurs est déclaré recevoir un t_joueur or il me semble que c'est un tableau de t_joueur que tu veux envoyer.
mais c'est ce que je fais non ? j'initialise mon tableau dans mon main et je l'envoie dans ma fonction ??? que faire ???
Ce n'est qu'une question de vocabulaire, mais en C, "initialiser" a un sens précis.
int tableau_non_initialise[3];
int tableau_initialise[3] = { 4, 5, 6 };
Dans ta fonction main, le tableau n'est pas initialisé.
Ensuite, le second argument passé à creation_structures_joueurs est un pointeur sur le premier élément du tableau. En effet, si tu te souviens du cours, quand on utilise un identifiant de tableau dans une expression, ça produit généralement un pointeur sur son premier élément.
Le gros problème est dans le prototype de fonction
int creation_structures_joueurs(int x, t_joueur joueur_x)
Le second paramètre devrait être de type pointeur de t_joueur. Or il est de type t_joueur.
Tu as deux façons pour le dire: int creation_structures_joueurs(int x, t_joueur *joueur_x) int creation_structures_joueurs(int x, t_joueur joueur_x[]) Dans la seconde forme, la notion de pointeur est moins explicite.
Le Tout est souvent plus grand que la somme de ses parties.
Je préfère la seconde forme. Parler de pointeurs dans ce contexte risque d'embrouiller les gens, je trouve plus simple de juste parler de tableaux.
On veut appeler la fonction ainsi :
creation_structures_joueurs(x, joueur_x);
Paramètre n°1 : 'x' est un 'int'
Paramètre n°2 : 'joueur_x' est un tableau dont les éléments sont des 't_joueur'.
Donc la fonction doit être déclarée ainsi :
int creation_structures_joueurs(int x, t_joueur joueur_x[])
Et voilà.
Les crochets indiquent qu'il s'agit d'un tableau (on ne met pas la taille dans les crochets), il ne faut pas donc les oublier : c'était l'erreur de Clément2910.
Pas besoin de parler de pointeur, c'est transparent pour le programmeur.
Pas besoin de parler de pointeur, c'est transparent pour le programmeur.
On n'a rien à cacher, il a le droit de savoir la vérité !
D'autant que la notation tableau est finalement mensongère; Car c'est bien un pointeur qui passé. Justement pour un débutant, la notation pointeur permet de lui rappeler qu'un tableau n'est jamais passé en paramètre. La notation tableau précise l'intention et est à préférer dans des applications plus "professionnelles".
Et, sans entrer trop dans un HS, je plussoie Robun et Dalfab et … la future norme C23 qui recommande l'utilisation de la notation VLA pour éclaircir les intentions en les explicitant dans le prototype des fonctions comme par exemple :
float determinant(size_t m, size_t n, float matrix[n][m]);
Ah ben non ! c'est bien pour cela que j'ai donné le lien qui «rétablit la vérité»
En fait une fois qu'on comprend la différence entre «tableau» et «pointeur» on remarque que mis à part en utilisant un tableau avec sizeof ou l'opérateur unaire &, il sera toujours converti en un pointeur sur son premier élément (norme paragraphe 6.3.2.1.3).
Ce que je disais, c'était dans le contexte de cette discussion : Clément2910 a besoin de transmettre des tableaux à sa fonction, comment faire ?
Je ne dis pas qu'il faut cacher que ce sont en fait des pointeurs qui sont transmis. Mais il y a une différence entre utiliser des tableaux et savoir comment ils sont gérés, de même qu'entre conduire une voiture et savoir comment fonctionne le moteur.
L'erreur faite par Clément2910 n'était pas liée aux pointeurs, elle provenait d'une confusion sur l'utilisation des crochets (dans une déclaration ça désigne un tableau, mais dans un appel ça désigne un seul élément).
En fait une fois qu'on comprend la différence entre «tableau» et «pointeur» on remarque que mis à part en utilisant un tableau avec sizeof ou l'opérateur unaire &, il sera toujours converti en un pointeur sur son premier élément (norme paragraphe 6.3.2.1.3).
Attention, il faut ajouter que ce pointeur sur le premier élément n'est pas une lvalue. C'est une erreur que les débutants font très souvent dans ce site. Par exemple:
struct s {
char str[10];
int foo;
};
void f(struct s *ps) {
ps->str = "toto"; // Mais pk ça marche pas ?
ps->foo = 123;
}
- Edité par Marc Mongenet 23 décembre 2021 à 2:32:11
L'affectation bar = "abc" a un résultat assez douteux quand bar est un pointeur reçu en paramètre (passage par valeur...)
Y en a pas un qui est mieux que l'autre, sauf qu'effectivement, le débutant peut s'imaginer, avec [], qu'il a réussi à affecter le contenu d'un tableau.
---
C'était juste pour évoquer un truc merdique de C (et d'ailleurs je m'y suis mal pris alors je recommence, le travail bâclé contient sa propre punition) :
la déclaration
int t[10]
déclare un pointeur quand c'est un paramètre
et un tableau de 10 entiers quand c'est une variable locale ou globale
Pour pinailler c'est un poil plus complexe si on regarde la norme (6.7.6 sections 2 et 3).
void foo(int a[10] /*ici, au niveau de la visibilité du prototype a est de type tableau d'entiers, quoique … clang/gcc ont un point de vue différent de msvc/icc par exemple */) {
// ici, au niveau du bloc de la fonction, a est ajusté en un pointeur sur le premier élément du tableau
int b[10]; // tableau
size_t s = sizeof(b); // b est un tableau
b[0]=42; // b est ajusté en pointeur sur entier pointant sur le premier élément du tableau b
// cette écriture est strictement équivalente à :
*(b+0)=42 // où b est à nouveau ajusté en …
....
}
Adresses et tableau, prend les mauvaises valeurs..
× Après avoir cliqué sur "Répondre" vous serez invité à vous connecter pour que votre message soit publié.
× Attention, ce sujet est très ancien. Le déterrer n'est pas forcément approprié. Nous te conseillons de créer un nouveau sujet pour poser ta question.
Le Tout est souvent plus grand que la somme de ses parties.
Le Tout est souvent plus grand que la somme de ses parties.
OK J'AI COMPRIS, mais pourquoi ici le gets ya une erreur et pareil pour les 2 lignes apres (suscribed value is not an array, pointer or vector...)
Le Tout est souvent plus grand que la somme de ses parties.
En recherche d'emploi.