Hobiecat a écrit : ↑14 mars 2022 23:32
Mais cet algorithme est très efficace, quand je compare les temps que j'ai indiqués plus haut et ceux que tu indiques
Oui, on parle bien d'environ ~8s pour 220313 et ~50s pour 20220313 ?
10 DESTROY ALL @ DELAY 0,0 @ INPUT C @ T=TIME
12 FOR D=1 TO SQR(C) STEP 2
14 IF NOT MOD(C,D) THEN GOSUB 20
16 NEXT D @ DISP "Nb:";N; @ GOSUB 22 @ END
20 N=N+1 @ DISP ABS(C/D-D)/2;
22 DISP '('&STR$(TIME-T)&'")'; @ RETURN
[RUN] 20220313 [END LINE] affiche sur mon HP-71B
10110156 (.18") 532104 (.54") 61944 (2.11") 1716 (30.14")Nb: 4 (43.5")
C'est à dire que la boucle prend 43.5 secondes.
Hobiecat a écrit : ↑14 mars 2022 23:32Ça pourrait d'ailleurs être un critère discriminant de MPO, à nombre de pas égaux : celui qui va le plus vite !
Tout à fait ! Combien de fois je me suis fais avoir pa run code qui me paraissait plus malin et que j'espérais plus rapide ou efficace alors qu'il n'apportait aucun gain , voir au contraire une perte d'efficacité ou célérité par rapport au code plus simple mais plus court et donc bien mieux !
zpalm a écrit : ↑15 mars 2022 06:18Bien vu l’utilisation de MOD.
Oui, je donnerai demain quelques explications, cela provient de la méthode de résolution que je détaillerai.
zpalm a écrit : ↑15 mars 2022 06:18Bien vu l’utilisation de MOD.
Intéressant, combien de solutions trouves-tu pour 14725 en utilisant PRIM ?[/quote]
Oui, intéressant pour 220313 et 20220313, car dans le cas général l'utilisation que je fais de PRIM est licencieuse !
Comme le démontre parfaitement l'exemple avec 14725. Mais même avec 45 mon utilisation licencieuse est mise en défaut et je ne trouve pas pour ces deux nombre toutes les solutions !
En effet, contrairement à 14725, la décomposition en facteurs premiers de 20220313 ou 220313 ne conduit à aucun facteur multiple :
20220313 = 19*163*6529 et 220313 = 29*71*107
Pour ces deux nombres l'utilisation de PRIM est donc simple et directe et prend moins de deux secondes :
10 DESTROY ALL @ DELAY 0,0 @ D=1 @ P=1 @ INPUT C @ T=TIME
12 WHILE D @ GOSUB 20 @ P=P*D @ D=PRIM(C/P) @ END WHILE
14 D=C/P @ GOSUB 20 @ DISP "Nb:";N; @ GOSUB 22 @ END
20 N=N+1 @ DISP ABS(C/D-D)/2;
22 DISP '('&STR$(TIME-T)&'")'; @ RETURN
[RUN] 20220313 [END LINE] affiche sur mon HP-71B
10110156 (.15") 532104 (.39") 61944 (.69") 1716 (.98")Nb: 4 (1.14")
Mais pour 45 ou 14725, on obtient, avec ce code fallacieux, des résultats erronés :
[RUN] 45 [END LINE] affiche quatre solution au lieu de trois en répétant inutilement la solution n=6 :
22 (.12") 6 (.31") 6 (.51") 2 (.71")Nb: 4 (.86")
[RUN] 14725 [END LINE] affiche uniquement quatre solutions au lieu des six solutions attendues en répétant inutilement la solution n=1470:
7362 (.14") 1470 (.35") 1470 (.57") 378 (.71") 222 (1")Nb: 5 (1.14")
Cela provient bien évidemment du facteur multiple.
Donc, pour traiter convenablement le cas général, il faut un code un peu plus élaboré et je ne suis pas sûr que le gain de temps par rapport à la simple boucle FOR TO STEP / NEXT soit significatif.
Je n'ai pas essayé. L'idée serai de créer la liste des diviseurs au fur et à mesure que l'instruction PRIM nous fournit les facteurs
Schraf a écrit : ↑15 mars 2022 14:24
Comme
je suis en train de travailler sur les HP-48/49/50G, avec les DOLIST, MAP... voici ma contribution pour cette question (uniquement pour les 49 et 50g car les 48G ne connaissent pas DIVIS). Attention également, il faut être en
MODE CAS Exact (décocher Approx)
L'idée de filtrer la liste me parait un peu compliquée. Si j'avais une instruction DIVIS et REVLIST sur mon HP-28S, j'aurais listé les solutions avec un code qui ressemblerai à cela:
C'est d'ailleurs le code que j'ai actuellement dans mon HP Prime :
Code : Tout sélectionner
EXPORT QDD(n)
BEGIN
LOCAL dv:=mat2list(idivis(n));
LOCAL re:=(REVERSE(dv)-dv)/2;
RETURN re[{1,SIZE(re)/2}];
END;
Marge a écrit : ↑15 mars 2022 16:10
Bonjour, voici comment j'ai résolu ce petit problème.
npg220313.png
Très chouette ce schéma, il est tard, j'expliquerai ma méthode demain
Avec un peu de chance, je trouverai aussi à faire quelques schémas