bonsoir , quelqu'un peut il m'aider sur cet exercice?
Un nombre parfait est égal à la somme de ses diviseurs, sauf lui-même. Exemples : 6 = 1 + 2 + 3, 28 = 1 + 2 + 4 + 7 + 14 .
chercher les entiers parfaits dans un intervalle [inf, sup] donné, afficher un message s'il n'y en a pas. Contrôler à la saisie les bornes de
//l'intervalle (inf<sup). REM. : 6 et 28 sont les deux seuls nombres parfaits de l'intervalle [1, 100].
j'ai essaye de le faire mais après execution sur les bornes [1,100] j'ai eu le message pas de nombre parfait dans cet intervalle bien qu'il ya le 6 et le 28 qui le sont.
#include<stdio.h>
void main(){
int a, b, somme=0, i, j, k=0; //i nombre a tester s'il est parfait
do{printf("veiller entrer les bornes d'un interval[a;b]\n a=?\n b=?\n");
scanf("%d",&a);
scanf("%d",&b);}while(b<=a);
for (i=a; i<=b; i++){
for(j=1;j<i; j++){
if(i% j==0){somme+=j;}
}
if(somme==i) printf("%d est parfait",i);
else k=1;
}
if(k=1){printf("pas de nombre parfait dans un intervalle saisi");}
getch();
}
merci d'avance .
Bonjour ,
même erreur déja rencontrée
tu dois calculer la somme des diviseurs de i
pas de tous les diviseurs de tous les nombres testés
Voila un algo écrit sur Algobox.
VARIABLES
Nmin EST_DU_TYPE NOMBRE
Nmax EST_DU_TYPE NOMBRE
N EST_DU_TYPE NOMBRE
S EST_DU_TYPE NOMBRE
Q EST_DU_TYPE NOMBRE
i EST_DU_TYPE NOMBRE
k EST_DU_TYPE NOMBRE
flag EST_DU_TYPE NOMBRE
DEBUT_ALGORITHME
AFFICHER "Entrez Nmin >= 2"
LIRE Nmin
LIRE Nmax
flag PREND_LA_VALEUR 0
POUR k ALLANT_DE Nmin A Nmax
DEBUT_POUR
N PREND_LA_VALEUR k
S PREND_LA_VALEUR 0
POUR i ALLANT_DE 1 A floor(sqrt(N))
DEBUT_POUR
Q PREND_LA_VALEUR N/i
SI (Q == floor(Q)) ALORS
DEBUT_SI
S PREND_LA_VALEUR S + i + Q
FIN_SI
FIN_POUR
SI (S-N == N) ALORS
DEBUT_SI
flag PREND_LA_VALEUR 1
AFFICHER N
AFFICHER* " est un nombre parfait"
FIN_SI
FIN_POUR
SI (flag == 0) ALORS
DEBUT_SI
AFFICHER* "Pas de nombre parfait dans l'intervalle demandé"
FIN_SI
FIN_ALGORITHME
oui tu dois initialiser somme dans la boucle "for i"
(la remettre à zéro à chaque nombre dont on veut calculer la somme des diviseurs)
bonsoir J-P
j'ai un peu du mal a comprendre ce qu'il y a ecrit dans cet algo comme on a pas etudier l'algo de plus je ne comprend pas tout les variables ( S,N,Q,i...)
mais mercii!!
et encore une question si vous pouvez m'aidez
if (k = 1) est toujours true (cela met 1 dans k quelle que soit sa valeur précédente, et la valeur de cette expression toute entièr est 1 c'est à dire true)
piège classique avec les "="
J-P : ton algorithme est défectueux
ça ne se voit pas car aucun nombre parfait n'est un carré,
mais il n'empêche que le calcul de la somme des diviseurs de N donne un résultat erroné si N est un carré parfait.
l'erreur est archi classique. tout le monde tombe dedans régulièrement sur faute de frappe.
quand on sait où chercher on la détecte rapidement (et peut être bien qu'il y a des compilo qui sortent un warning la dessus)
ce n'est pas if (k = 1) mais if (k == 1)
(l'opérateur de comparaison et pas l'opérateur d'affectation)
Bonsoir. Ma proposition :
#include<stdio.h>
int main()
{
int binf = 0 ;
int bsup = 0 ;
int nombre_teste = 0 ;
int somme_diviseurs = 0 ;
int nombre_diviseurs = 0 ;
int nombre_parfaits = 0 ;
int diviseur ;
printf(" Recherche des nombres parfaits dans l'intervalle [inf, sup]...\n\n") ;
printf(" > Entrez la borne inferieure de l'intervalle Binf :\n") ;
scanf("%d", &binf) ;
printf(" > Entrez la borne superieure de l'intervalle Bsup :\n") ;
scanf("%d", &bsup) ;
printf("\n") ;
// balayage des nombres entre inf et sup
for (nombre_teste = binf ; nombre_teste <= bsup ; nombre_teste++)
{
printf(" > Nombre en test : % 6d \t Diviseur(s) : ", nombre_teste) ;
somme_diviseurs = 0 ;
nombre_diviseurs = 0 ;
// recherche des diviseurs
for (diviseur = 1 ; diviseur < nombre_teste ; diviseur++)
{
if (diviseur == 1)
{
somme_diviseurs += 1 ;
nombre_diviseurs += 1 ;
printf("%d ", diviseur) ;
}
// diviseur de nombre ?
else if (nombre_teste % diviseur == 0)
{
somme_diviseurs += diviseur ;
nombre_diviseurs += 1 ;
printf("%d ", diviseur) ;
}
}
if ((nombre_teste == somme_diviseurs) && (nombre_diviseurs > 0))
{
printf("\t Nombre %d est parfait", nombre_teste) ;
nombre_parfaits += 1 ;
}
printf("\n") ;
}
if (nombre_parfaits == 0)
{
printf("\n Pas de nombre parfait dans l'intervalle saisi") ;
}
return(0) ;
}
il y a des trucs trop compliqués là dedans n%1 = 0 quel que soit n entier (en d'autres termes 1 divise bien n quel que soit n, le reste de la division entière de n par 1 est 0)
il n'y a aucune raison de faire un cas particulier de diviseur == 1 ou pas
de plus la consigne :
"Contrôler à la saisie les bornes de l'intervalle (inf(c'est la boucle do{ ...}while(b<=a); du programme de Rana)
le programme est "verbeux" puisqu'il donne une (longue) liste de tous les nombres entiers de min à max parfaits ou pas, avec la liste exhaustive de leurs diviseurs et avec par ci par là un message supplémentaire "ce nombre [redite] est parfait"
bref la sortie est assez inutilisable si on demande de trouver les nombres parfaits entre 1 et 10000 par exemple,
genre chercher l'aiguille dans la botte de listing.
Bonjour.
Version plus orthodoxe :
#include<stdio.h>
int main()
{
int binf = 0 ;
int bsup = 0 ;
int nombre_teste = 0 ;
int somme_diviseurs = 0 ;
int nombre_parfaits = 0 ;
int diviseur ;
printf(" Recherche des nombres parfaits dans l'intervalle [Binf, Bsup]...\n\n") ;
do
{
printf(" > Entrez la borne inferieure de l'intervalle Binf :\n") ;
scanf("%d", &binf) ;
printf(" > Entrez la borne superieure de l'intervalle Bsup :\n") ;
scanf("%d", &bsup) ;
} while (bsup <= binf) ;
printf("\n Liste des nombres parfaits :\n\n") ;
// balayage des nombres entre Binf et Bsup
for (nombre_teste = binf ; nombre_teste <= bsup ; nombre_teste++)
{
somme_diviseurs = 0 ;
// recherche des diviseurs de nombre_teste
for (diviseur = 1 ; diviseur < nombre_teste ; diviseur++)
{
// diviseur ?
if (nombre_teste % diviseur == 0)
{
somme_diviseurs += diviseur ;
}
}
// nombre_teste parfait ?
if (nombre_teste == somme_diviseurs)
{
nombre_parfaits += 1 ;
printf("\t%d\n", nombre_teste) ;
}
}
if (nombre_parfaits == 0)
{
printf("\n Pas de nombre parfait dans l'intervalle saisi") ;
}
return(0) ;
}
Mon "défectueux" était très exagéré.
juste que dans sa boucle interne il ne calcule pas la somme des diviseurs de n
mais "autre chose" qui est "parfois" (la plupart du temps il est vrai) la somme des diviseurs, en particulier si le nombre est parfait.
prouver la justesse de cet algorithme est donc plus difficile (nécessite à priori des connaissances sur les propriétés théoriques des nombres parfaits au lieu de les chercher par force brute)
il a été démontré ?
ah bon je ne dois pas être au fait des dernières avancées en ce domaine.
il a été démontré que si un nombre pair est parfait il est de la forme ...
(et d'ailleurs réciproquement que si un nombre est de cette forme avec (2^n - 1) premier, nombre premier de Mersenne, alors il est parfait)
à ma connaissance on n'a pas prouvé l'inexistence de nombres parfaits impairs, même si on n'en a jamais trouvé.
tant qu'à faire au lieu de tester les nombres un par un et de calculer la somme des diviseurs, tu pouvais te contenter de ces seuls nombre là
Si on veut boucher le trou très probablement inexistant ...
VARIABLES
Nmin EST_DU_TYPE NOMBRE
Nmax EST_DU_TYPE NOMBRE
N EST_DU_TYPE NOMBRE
S EST_DU_TYPE NOMBRE
Q EST_DU_TYPE NOMBRE
i EST_DU_TYPE NOMBRE
k EST_DU_TYPE NOMBRE
flag EST_DU_TYPE NOMBRE
DEBUT_ALGORITHME
AFFICHER "Entrez Nmin >= 2"
LIRE Nmin
LIRE Nmax
flag PREND_LA_VALEUR 0
POUR k ALLANT_DE Nmin A Nmax
DEBUT_POUR
N PREND_LA_VALEUR k
S PREND_LA_VALEUR 0
POUR i ALLANT_DE 1 A floor(sqrt(N))
DEBUT_POUR
Q PREND_LA_VALEUR N/i
SI (Q == floor(Q)) ALORS
DEBUT_SI
S PREND_LA_VALEUR S + i + Q
SI (Q == i) ALORS
DEBUT_SI
S PREND_LA_VALEUR S - i
FIN_SI
FIN_SI
FIN_POUR
SI (S-N == N) ALORS
DEBUT_SI
flag PREND_LA_VALEUR 1
AFFICHER N
AFFICHER* " est un nombre parfait"
FIN_SI
FIN_POUR
SI (flag == 0) ALORS
DEBUT_SI
AFFICHER* "Pas de nombre parfait dans l'intervalle demandé"
FIN_SI
FIN_ALGORITHME
Vous devez être membre accéder à ce service...
Pas encore inscrit ?
1 compte par personne, multi-compte interdit !
Ou identifiez-vous :