FORUM DE DISCUSSION SUR LE LANGAGE PANORAMIC

Développement d'applications avec le langage Panoramic
 
AccueilAccueil  FAQFAQ  RechercherRechercher  S'enregistrerS'enregistrer  MembresMembres  GroupesGroupes  Connexion  
Derniers sujets
» Tout est tranquille
par Jean Claude Hier à 21:41

» Texte en gif animé
par JL35 Hier à 13:29

» BasicEditor
par Yannick Mer 20 Sep 2017 - 17:17

» Simuler l’appui d'une touche ou combinaison de touches.
par pascal10000 Lun 18 Sep 2017 - 19:30

» Utilisation de HVIEWER pour afficher des images
par papydall Lun 18 Sep 2017 - 17:43

» Panoramic et les gifs animés.
par papydall Lun 18 Sep 2017 - 16:32

» recover source
par pascal10000 Dim 17 Sep 2017 - 14:21

» Recent dans vos menu
par Jean Claude Sam 16 Sep 2017 - 11:41

» Comment centrer un texte 3D.
par pascal10000 Ven 15 Sep 2017 - 20:20

» Carte interface 16 entrées et 16 sorties
par Jicehel Ven 15 Sep 2017 - 16:30

» Version instantanée V 0.9.28i9 possédant l'objet SYNEDIT
par pascal10000 Ven 15 Sep 2017 - 16:20

» Compilateur FBPano
par jean_debord Ven 15 Sep 2017 - 9:59

» 1 (en analyse): 3D_TARGET_IS ne fonctionne pas sur 3D_TEXT
par Jack Jeu 14 Sep 2017 - 19:52

» Problème avec la 3D.
par Jack Jeu 14 Sep 2017 - 18:06

» Test de la 3D.
par mindstorm Mer 13 Sep 2017 - 19:45

Navigation
 Portail
 Index
 Membres
 Profil
 FAQ
 Rechercher
Rechercher
 
 

Résultats par :
 
Rechercher Recherche avancée
Septembre 2017
LunMarMerJeuVenSamDim
    123
45678910
11121314151617
18192021222324
252627282930 
CalendrierCalendrier

Partagez | 
 

 Adresses dans un tableau à 2 dimensions

Voir le sujet précédent Voir le sujet suivant Aller en bas 
AuteurMessage
Klaus

avatar

Nombre de messages : 10062
Age : 68
Localisation : Ile de France
Date d'inscription : 29/12/2009

MessageSujet: Adresses dans un tableau à 2 dimensions   Dim 13 Nov 2016 - 5:30

A ce jour, pour un tableau en Panoramic, on peut utiliser la fonction ADR() .

Pour un tableau d'une seule dimension, elle retourne l'adresse de la case (0), et toutes les autres cases occupent les cellules juste à la suite.

Pour un tableau de deux dimensions, elle retourne l'adresse de la case (0,0), et les adresses (1,0), ... jusqu'à (n,0) se trouvent juste à la suite. Mais l'adresse de la cellule (1,0) ? Et (2,0) et ainsi de suite ? Mystère.

J'avais fait une suggestion de nouvelle fonction solvant ce problème, et je verrai bien si Jack a le temps et l'envie de faire quelque chose dans ce domaine. En attendant, j'ai trouvé une astuce, avec l'aide de KGF.dll, pour contourner ce manque. Je peux trouver les adresses de ces cellules (et donc accéder au "vecteur" concernant chaque valeur du premier indice), pour un tableau d'entiers. Pour les flottants et les chaînes de caractères ma méthode pourra être étendue également.

En voici une démo:
Code:
' trouver_les_series_pour_un_tableau_de_entiers.bas
dim debug% : debug% = 0
dim i%, j%, k%, a$, res%
width 0,1200 : height 0,600
dll_on "KGF.dll"
memo 2 : left 2,                 10 : width 2,200 : height 2,500 : bar_vertical 2
memo 3 : left 3,left(2)+width(2)+10 : width 3,400 : height 3,500 : bar_vertical 3 : if debug%=0 then hide 3
memo 4 : left 4,left(3)+width(3)+10 : width 4,300 : height 4,500 : bar_vertical 4 : if debug%=0 then hide 4


res% = dll_call1("LocalizePanoramicSymbolTable",adr(number_click))

' définition d'un premier tableau
dim test%(4,5) : ' , test1%(3,4)

' définition du deuxième tableau
dim buf%(4,2100)

' définition d'un troisième tableau
dim essai%(4,4)


tester(1)
tester(2)
tester(3)

end

sub tester(cas%)
  dim_local a%(5), res%, n%, s$

for n%=0 to 4
 select cas%
   case 1
     s$ = "test%("+str$(n%)+",0)"
     test%(n%,0)  = hex("FF77CC00")+1
     test%(n%,1)  = hex("FF77CC00")+2
     a%(n%) = dll_call4("FindValueInVirtualMemory",0,0,test%(n%,0),test%(n%,0))
     res% = dll_call3("DumpPanoramic",handle(4),a%(n%)-40,40) : ' dump de cette section
     item_add 3, "FindValueInVirtualMemory: adr("+s$+")="+right$("0000000"+hex$(a%(n%)),8)
     item_add 3,"adr("+s$+"="+hex$(a%(n%))+"  entête="+hex$(a%(n%)-40)
     item_add 4,"================================"
     test%(n%,0)  = 0
     test%(n%,1)  = 0
   case 2
     s$ = "buf%("+str$(n%)+",0)"
     buf%(n%,0)   = hex("FF77CC00")+1
     buf%(n%,1)   = hex("FF77CC00")+2
     a%(n%) = dll_call4("FindValueInVirtualMemory",0,0,buf%(n%,0),buf%(n%,0))
     res% = dll_call3("DumpPanoramic",handle(4),a%(n%)-40,40) : ' dump de cette section
     item_add 3, "FindValueInVirtualMemory: adr("+s$+")="+right$("0000000"+hex$(a%(n%)),8)
     item_add 3,"adr("+s$+"="+hex$(a%(n%))+"  entête="+hex$(a%(n%)-40)
     item_add 4,"================================"
     buf%(n%,0)   = 0
     buf%(n%,1)   = 0
   case 3
     s$ = "essai%("+str$(n%)+",0)"
     essai%(n%,0) = hex("FF77CC00")+1
     essai%(n%,1) = hex("FF77CC00")+2
     a%(n%) = dll_call4("FindValueInVirtualMemory",0,0,essai%(n%,0),essai%(n%,0))
     res% = dll_call3("DumpPanoramic",handle(4),a%(n%)-40,40) : ' dump de cette section
     item_add 3, "FindValueInVirtualMemory: adr("+s$+")="+right$("0000000"+hex$(a%(n%)),8)
     item_add 3,"adr("+s$+"="+hex$(a%(n%))+"  entête="+hex$(a%(n%)-40)
     item_add 4,"================================"
     essai%(n%,0) = 0
     essai%(n%,1) = 0
 end_select
next n%

 select cas%
   case 1
     item_add 2,"dim test%(4,5)"
   case 2
     item_add 2,"dim buf%(4,2100)"
   case 3
     item_add 2,"dim essai%(4,4)"
 end_select

if debug%<>0
 item_add 2,"a2-a1="+right$("0000000"+hex$(a%(1)-a%(0)),8)+"="+str$(a%(1)-a%(0))
 item_add 2,"a3-a2="+right$("0000000"+hex$(a%(2)-a%(1)),8)+"="+str$(a%(2)-a%(1))
 item_add 2,"a4-a3="+right$("0000000"+hex$(a%(3)-a%(2)),8)+"="+str$(a%(3)-a%(2))
 item_add 2,"a5-a4="+right$("0000000"+hex$(a%(4)-a%(3)),8)+"="+str$(a%(4)-a%(3))
 item_add 2,"--------------------------------"
end_if

for n%=0 to 4
  item_add 2,"adr indice "+str$(n%)+"="+hex$(a%(n%))
next n%
item_add 2,"========================"
item_add 3,"========================"
item_add 4,""
item_add 4,""
item_add 4,""
end_sub

Ce programme définit 3 tableaux, et trouve les adresses des cellules (n,0) pour chaque valeur de n.

Mais, ce que je n'ai pas encore trouvé, c'est l'endroit où est mémorisé la liste ce ces adresses, pour chaque tableau...

L'idéal serait évidemment que Jack implémente la fonction ADR_ARRAY().
Revenir en haut Aller en bas
Voir le profil de l'utilisateur http://klauspanoramic.comxa.com/index.html
Klaus

avatar

Nombre de messages : 10062
Age : 68
Localisation : Ile de France
Date d'inscription : 29/12/2009

MessageSujet: Re: Adresses dans un tableau à 2 dimensions   Mer 16 Nov 2016 - 2:19

Après une série d'essais, j'ai la conviction d'avoir trouvé une méthode pour localiser l'adresse du début des séries de cellules pour un tableau d'entiers (extensible aux tableaux de flottants et de chaînes de caractères, bien sûr). Mon petit ptogramme de démo a été étendu pour copier dans 5 fichiers binaires de 2101 mots de 32 bits (indices 0 à 2100) des 5 séries du tableau buf%(4,2100):
Code:
' trouver_les_series_pour_un_tableau_de_entiers.bas
dim debug% : debug% = 0              : ' 1=afficher des informations techniques
dim SaveArray% : SaveArray% = 1      : ' 1=écrire les séries de buf% dans des fichiers
dim i%, j%, k%, a$, res%
width 0,1200 : height 0,600
dll_on "KGF.dll"
memo 2 : left 2,                 10 : width 2,200 : height 2,500 : bar_vertical 2
memo 3 : left 3,left(2)+width(2)+10 : width 3,400 : height 3,500 : bar_vertical 3 : if debug%=0 then hide 3
memo 4 : left 4,left(3)+width(3)+10 : width 4,300 : height 4,500 : bar_vertical 4 : if debug%=0 then hide 4


res% = dll_call1("LocalizePanoramicSymbolTable",adr(number_click))

' définition d'un premier tableau
dim test%(4,5) : ' , test1%(3,4)

' définition du deuxième tableau
dim buf%(4,2100)

' définition d'un troisième tableau
dim essai%(4,4)


tester(1)
tester(2)
tester(3)

end

sub tester(cas%)
  dim_local a%(6), res%, n%, s$, ID%, i%, f$

for n%=0 to 4
 select cas%
   case 1
     s$ = "test%("+str$(n%)+",0)"
     test%(n%,0)  = hex("FF77CC00")+1
     test%(n%,1)  = hex("FF77CC00")+2
     a%(n%) = dll_call4("FindValueInVirtualMemory",0,0,test%(n%,0),test%(n%,0))
     res% = dll_call3("DumpPanoramic",handle(4),a%(n%)-40,40) : ' dump de cette section
     item_add 3, "FindValueInVirtualMemory: adr("+s$+")="+right$("0000000"+hex$(a%(n%)),8)
     item_add 3,"adr("+s$+"="+hex$(a%(n%))+"  entête="+hex$(a%(n%)-40)
     item_add 4,"================================"
     test%(n%,0)  = 0
     test%(n%,1)  = 0
   case 2
     s$ = "buf%("+str$(n%)+",0)"
     buf%(n%,0)   = hex("FF77CC00")+1
     buf%(n%,1)   = hex("FF77CC00")+2
     a%(n%) = dll_call4("FindValueInVirtualMemory",0,0,buf%(n%,0),buf%(n%,0))
     res% = dll_call3("DumpPanoramic",handle(4),a%(n%)-40,40) : ' dump de cette section
     item_add 3, "FindValueInVirtualMemory: adr("+s$+")="+right$("0000000"+hex$(a%(n%)),8)
     item_add 3,"adr("+s$+"="+hex$(a%(n%))+"  entête="+hex$(a%(n%)-40)
     item_add 4,"================================"
     if SaveArray%=1
       for i%=2 to 2100
         buf%(n%,i%) = hex("FF000000") + n%*hex("10000") + i%
       next i%
       f$ = "IntegerArray_4_2100_"+str$(n%)+".dat"
       if file_exists(f$)=1 then file_delete f$
       ID% = dll_call2("ConnectToBinaryFile",adr(f$),2)
       res% = dll_call4("WriteFileFromIntegerArray32",ID%,a%(n%),0,2100)
       res% = dll_call1("DisconnectFromBinaryFile",ID%)
     end_if
     buf%(n%,0)   = 0
     buf%(n%,1)   = 0
   case 3
     s$ = "essai%("+str$(n%)+",0)"
     essai%(n%,0) = hex("FF77CC00")+1
     essai%(n%,1) = hex("FF77CC00")+2
     a%(n%) = dll_call4("FindValueInVirtualMemory",0,0,essai%(n%,0),essai%(n%,0))
     res% = dll_call3("DumpPanoramic",handle(4),a%(n%)-40,40) : ' dump de cette section
     item_add 3, "FindValueInVirtualMemory: adr("+s$+")="+right$("0000000"+hex$(a%(n%)),8)
     item_add 3,"adr("+s$+"="+hex$(a%(n%))+"  entête="+hex$(a%(n%)-40)
     item_add 4,"================================"
     essai%(n%,0) = 0
     essai%(n%,1) = 0
 end_select
next n%

 select cas%
   case 1
     item_add 2,"dim test%(4,5)"
   case 2
     item_add 2,"dim buf%(4,2100)"
   case 3
     item_add 2,"dim essai%(4,4)"
 end_select

if debug%<>0
 item_add 2,"a2-a1="+right$("0000000"+hex$(a%(1)-a%(0)),8)+"="+str$(a%(1)-a%(0))
 item_add 2,"a3-a2="+right$("0000000"+hex$(a%(2)-a%(1)),8)+"="+str$(a%(2)-a%(1))
 item_add 2,"a4-a3="+right$("0000000"+hex$(a%(3)-a%(2)),8)+"="+str$(a%(3)-a%(2))
 item_add 2,"a5-a4="+right$("0000000"+hex$(a%(4)-a%(3)),8)+"="+str$(a%(4)-a%(3))
 item_add 2,"--------------------------------"
end_if

for n%=0 to 4
  item_add 2,"adr indice "+str$(n%)+"="+hex$(a%(n%))
next n%
item_add 2,"========================"
item_add 3,"========================"
item_add 4,""
item_add 4,""
item_add 4,""

end_sub

Le résultat est correct. Mais la méthode est brutale et a quelques inconvénients. En particulier, si le tableau est supprimé via la commande FREE et recréé par DIM, les adresses doivent évidemment être recherchées à nouveau, ce qui pose le problème de la pérennité de ces valeurs.

Ceci, comme déjà indiqué dans un autre post, pourrait être résolu de deux manières:
1. création d'une fonction ADR_ARRAY(N,I1,I2) avec N=nom du tableau, I1 et I2 étant des indices
2. mémorisation de façon physiquement contigue des séries de données

Personnellement, à la vue de la gestion del'allocation de mémoire dynamique de Panoramic, je pense que la solution (2) est exclue. Par contre, une fonction ADR_ARRAY(N,I1,I2) est certainement faisable assez facilement:
Code:
dim a%, buf%(30,50)
a% = adr_array(buf%,3,0) : ' retourne l'adresse du début de la série 3 = cellule buf%(3,0)
a% = adr_array(buf%,17,23) : ' retourne l'adresse de la cellule buf%(17,23)

Un des objectifs de cette suggestion (mais pas le seul !) est de pouvoir faire des sauvegardes et restaurations très rapides des données de gros tableaux.

D'ailleurs, pour les 3 types de tableaux, les informatioins suivantes s'appliquent:
1. tableaux d'entiers: chaque cellule est un mot de 32 bits contenant un entier signé
2. tableau de flottants: chaque cellule est un mont long de 64 bits contenant un flottant
3. tableau de chaînes de caractères: chaque cellule est un mot de 32 bits contenant un pointeur de type pstring adresse de la chaîne de caractères terminée par un octet 0 et précédée de 2 mots contenant longueur et compteur d'utilisation

EDIT

Il va de soi que ce programme de démo a besoin de la version actuelle de KGF.dll, disponible au téléchargement sur mon site, mon site miroir ou mon WebDav, ainsi que par le lien dans ma signature !

P.S.

Ou est-ce qu'il y aurait un moyen, dans une DLL, de trouver les adresses des débuts des sections pour un tableau en deux dimensions ? A partir du nom d'une variable en chaîne de caractères, je peux retrouver son nombre de dimensions (0, 1 ou 2) et la ou les valeurs de ses dimensions (1 ou 2 valeurs). Mais les adresses de départ des sections de données pour chacune des valeurs du second indice ? Je n'ai pas encore réussi à trouver cela à partir de la DLL...
Revenir en haut Aller en bas
Voir le profil de l'utilisateur http://klauspanoramic.comxa.com/index.html
 
Adresses dans un tableau à 2 dimensions
Voir le sujet précédent Voir le sujet suivant Revenir en haut 
Page 1 sur 1
 Sujets similaires
-
» Ajouter un texte et des infobulles dans un tableau
» Symboles disparaissent dans un tableau
» Aller à la ligne dans un tableau
» Mettre une image de fond dans un tableau.
» Insérer image et nombres dans un tableau

Permission de ce forum:Vous ne pouvez pas répondre aux sujets dans ce forum
FORUM DE DISCUSSION SUR LE LANGAGE PANORAMIC :: PANORAMIC :: Présentation et bavardage-
Sauter vers: