IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

C Discussion :

fonction booleénne minmax


Sujet :

C

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre confirmé
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Mars 2017
    Messages
    176
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Gironde (Aquitaine)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : Conseil

    Informations forums :
    Inscription : Mars 2017
    Messages : 176
    Par défaut fonction booleénne minmax
    Bonjour,

    Pas trop de connaissance en C, je cherche à écrire une fonction minmax qui prend en paramètres un tableau d'entiers, la taille et les adresses des variables min et max.

    Je voudrais que cette fonction me retourne un booléan si le calcul a pu être efféctué et modifie les variables pointées en leur affectant respectivement le plus petit et le plus grand élément du tableau.

    J'ai pensé à faire un truc comme ceci:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
     
    #include <stdio.h> /* utilisation de la librairie stdio.h pour pouvoir utiliser un
     
    bool minmax(int a_Array[], int a_Size, int* a_Min, int* a_Max)
    {
        int i, iMin, iMax;
         
        *a_Min = *a_Max = 0;
         
         
        if(a_Size > 1)
        {
            iMin = iMax = a_Array[0];
            i = 0;
            while(i < a_Size)
            {
                if(a_Array[i] < iMin) iMin = a_Array[i];
                if(a_Array[i] > iMax) iMax = a_Array[i];    
                i++;
            }
            *a_Min = iMin;
            *a_Max = iMax;
            return true;
        }
     
        return false;
    }
    Merci,

  2. #2
    Expert confirmé
    Homme Profil pro
    Analyste/ Programmeur
    Inscrit en
    Juillet 2013
    Messages
    4 768
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Analyste/ Programmeur

    Informations forums :
    Inscription : Juillet 2013
    Messages : 4 768
    Par défaut
    Ton algo ne fonctionne pas il faut mettre un gros nombre pour le minimum. 0 sera toujours un minimum si tu le compares avec tous les nombres positifs

    Sinon, tu peux :
    • Replacer ta boucle while par une boucle for
    • Replacer tes 2 if ... if par un if ... else if. Si le nombre est un minimum, il ne sera jamais un maximum ... sauf si ton tableau ne contient que la même valeur. Pour ce cas, il faut juste initialiser le max avec la première valeur et mettre le test maximum dans le else
    • Je ne suis pas fan du return en plein milieu . Moi j'aurais codé *


    *, non compilé, non testé:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    unsigned char minmax(int input_tab[], size_t input_size, int* output_min, int* output_max) {
        unsigned char ret;
     
        if ((input_tab != NULL) && (output_min != NULL) && (output_max != NULL)) {
            switch(input_size) {
            case 0:
                *output_min = 0;
                *output_max = 0;
     
                ret = 0;
                break;
            case 1:
                *output_min = input_tab[0];
                *output_max = input_tab[0];
     
                ret = 1;
                break;
            default:
                {
                    size_t elt;
                    int min, max;
     
                    for(min=input_tab[0], max=input_tab[0], elt=1; elt < input_size; ++elt) {
                        if (input_tab[elt] < min) {
                            min = input_tab[elt];
                        } else if (input_tab[elt] > max) {
                           max = input_tab[elt];
                        }
                    }
     
                    *output_min = min;
                    *output_max = max;
     
                    ret = 1;
                }
                break;
            }
        } else {
            ret = 0;
        }
     
        return ret;
    }

  3. #3
    Membre Expert
    Avatar de Pyramidev
    Homme Profil pro
    Tech Lead
    Inscrit en
    Avril 2016
    Messages
    1 513
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Tech Lead

    Informations forums :
    Inscription : Avril 2016
    Messages : 1 513
    Par défaut
    Bonjour,

    Je pense qu'il est préférable d'interdire l'utilisateur d'appeler minmax avec un tableau vide.
    En effet, quand cela arrivera, ce sera probablement à cause d'une erreur de programmation.
    Or, pour aider à détecter les erreurs de programmation dans la phase de débogage, le langage C fournit la macro assert.

    Personnellement, voici comment j'aurais codé minmax :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    #include <assert.h>
    #include <stddef.h>
     
    typedef struct { int min, max; } minmax_result_t;
     
    minmax_result_t minmax(int const* nonEmptyArray, size_t size)
    {
    	assert(nonEmptyArray != NULL);
    	assert(size >= 1);
     
    	minmax_result_t result = {nonEmptyArray[0], nonEmptyArray[0]};
    	for(size_t k = 1; k < size; ++k) {
    		if     (result.min > nonEmptyArray[k]) result.min = nonEmptyArray[k];
    		else if(result.max < nonEmptyArray[k]) result.max = nonEmptyArray[k];
    	}
    	return result;
    }
     
    // Exemple d'utilisation :
     
    #include <stdio.h>
     
    int main()
    {
    	int const arrayTest[] = {2, -3, 3, -7, 7, -5, 5};
    	size_t const arrayTestSize = sizeof(arrayTest) / sizeof(int);
    	minmax_result_t const minAndMax = minmax(arrayTest, arrayTestSize);
    	printf("The minimum is %d and the maximum is %d.", minAndMax.min, minAndMax.max);
    	return 0;
    }

  4. #4
    Membre confirmé
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Mars 2017
    Messages
    176
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Gironde (Aquitaine)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : Conseil

    Informations forums :
    Inscription : Mars 2017
    Messages : 176
    Par défaut
    Merci beaucoup pour vos réponses. En effet, il me faut suivre la consigne telle que je l’ai définie à savoir une fonction qui prend 4 paramètres et qui me retourne un booléen si le calcul est possible. Pouvez-vous svp me confirmer aussi que l’etoile * devant les paramètres Min et Max signife que ces paramètres vont contenir les adresses comme demandé dans la consigne. J’ai remarqué aussi que personne n’a utilisé le type bool devant le nom de la fonction est ce parce que cela n’est pas possible dans le langage c?

  5. #5
    Membre Expert
    Avatar de Pyramidev
    Homme Profil pro
    Tech Lead
    Inscrit en
    Avril 2016
    Messages
    1 513
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Tech Lead

    Informations forums :
    Inscription : Avril 2016
    Messages : 1 513
    Par défaut
    Contrairement à ce que dit foetus, ton algo fonctionne. Je pense qu'il a lu trop vite et a sauté ton instruction iMin = iMax = a_Array[0];.
    L'étoile devant tes paramètres a_Min et a_Max signifie bien que ces paramètres vont contenir des adresses.
    bool existe bien en C, mais il faut inclure "stdbool.h".

    Si on est obligé d'avoir 4 paramètres et de retourner un booléen, alors j'aurais écrit ceci :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    #include <stdbool.h>
    #include <stddef.h>
     
    bool minmax(int const* array, size_t size, int* outMin, int* outMax)
    {
    	if(array == NULL || outMin == NULL || outMax == NULL || size < 1)
    		return false;
     
    	*outMin = *outMax = array[0];
    	for(size_t k = 1; k < size; ++k) {
    		if     (*outMin > array[k]) *outMin = array[k];
    		else if(*outMax < array[k]) *outMax = array[k];
    	}
    	return true;
    }
     
    // Exemple d'utilisation :
     
    #include <stdio.h>
     
    int main()
    {
    	int const arrayTest[] = {2, -3, 3, -7, 7, -5, 5};
    	size_t const arrayTestSize = sizeof(arrayTest) / sizeof(int);
    	int min, max;
    	bool const ok = minmax(arrayTest, arrayTestSize, &min, &max);
    	if(ok)
    		printf("The minimum is %d and the maximum is %d.", min, max);
    	else
    		printf("Programming error!");
    	return 0;
    }

  6. #6
    Membre confirmé
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Mars 2017
    Messages
    176
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 43
    Localisation : France, Gironde (Aquitaine)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : Conseil

    Informations forums :
    Inscription : Mars 2017
    Messages : 176
    Par défaut
    Merci pour votre réactivité mais le premier paramètre doit être un tableau d’entiers.

  7. #7
    Membre Expert
    Inscrit en
    Mars 2005
    Messages
    1 431
    Détails du profil
    Informations forums :
    Inscription : Mars 2005
    Messages : 1 431
    Par défaut
    J'ajouterais à la proposition de Pyramidev qu'il s'agit d'un cas où il peut être intéressant de spécifier restrict :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    void minmax(const int *restrict buf, size_t count, int *restrict minimum, int *restrict maximum);
    ..voire mieux, on renvoie le rang (ou l'adresse, c'est selon) des extrema :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    void minmax(const int *restrict buf, size_t count, size_t *restrict minrank, size_t *restrict maxrank);
    Si count vaut zéro, les valeurs des paramètres de sortie sont laissées inchangées. Sinon, la fonction ne peut pas échouer. Pourquoi renvoyer quoi que ce soit ? Ce n'est pas pertinent.

    Ou encore, en version générique :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    void minmax(const void *restrict buf, size_t count, size_t size, int (*cmp)(const void *, const void *), size_t *restrict minrank, size_t *restrict maxrank);

Discussions similaires

  1. Réponses: 2
    Dernier message: 18/03/2013, 13h20
  2. Réponses: 18
    Dernier message: 08/11/2009, 21h41
  3. [T-SQL] Fonction booléenne
    Par Fused dans le forum Développement
    Réponses: 2
    Dernier message: 04/08/2009, 11h35
  4. appeler fonction booléenne dans un select
    Par evaki07 dans le forum PL/SQL
    Réponses: 5
    Dernier message: 16/04/2009, 14h29
  5. Réécrire une fonction booléenne
    Par Maxence45 dans le forum Scheme
    Réponses: 8
    Dernier message: 07/02/2008, 20h10

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo