Les pointeurs!

Résolu
Samou85 Messages postés 46 Date d'inscription mardi 2 juin 2009 Statut Membre Dernière intervention 7 octobre 2009 - 6 juin 2009 à 10:52
Samou85 Messages postés 46 Date d'inscription mardi 2 juin 2009 Statut Membre Dernière intervention 7 octobre 2009 - 13 juin 2009 à 01:20
Bonjour à tous!

voilà je voudrais poser une question sur les pointeurs!

J'ai une tableau où chaque case contient un pointeur vers un autre tableau, et je voudrais supprimer des cases du tableau pricipal  et comment c'est un tableau de pointeurs je ne sais pas exactement comment je dois m'y prendre!
Merci de me répondre!

9 réponses

cs_rt15 Messages postés 3874 Date d'inscription mardi 8 mars 2005 Statut Modérateur Dernière intervention 7 novembre 2014 13
6 juin 2009 à 14:08
"si une case est supprimé je veux que celle qui vient juste aprés elle prenne sa place"

Dans ce cas faut décaler toutes les cases suivantes, pas juste celle d'après.
Ou suivre la proposition de Guillemouze.
3
cs_rt15 Messages postés 3874 Date d'inscription mardi 8 mars 2005 Statut Modérateur Dernière intervention 7 novembre 2014 13
6 juin 2009 à 11:11
Salut,

Manque de précision tout ça. Un peu de code pour nous aiguiller peut être ?

Ton tableau principal est un tableau dynamique ? Doit il être trié ? Doit tu conserver les autres éléments à leur place (Element situé en i+1 doit toujours être en i + 1 après la suppression de l'élément i) ?

La principale question que tu dois te poser -> faut il libérer le tableau pointer avant de supprimer la case ?

Une bonne technique de suppression dans un tableau est de recopier le dernier élément dans la case à supprimer et de signaler d'une manière ou d'une autre que le tableau a un élément de moins. Mais ce n'est pas toujours possible en fonction des contraintes que tu appliques à ton tableau (cf ci-dessus).
0
Samou85 Messages postés 46 Date d'inscription mardi 2 juin 2009 Statut Membre Dernière intervention 7 octobre 2009
6 juin 2009 à 12:24
Il est vrai que tu as raison "rt15" tout ça manque un peu de précision et de source je vais essayer d'etre plus clair:

type
    TTabTest= Array[1..10000] of integer;
    PTabTest= ^TTabTest;
    TPTabTest= Array[1..10000] of PTabTest;
Begin
TabAdj:TPTabTest;
end;

 en fait ce que je veux c'est supprimer certaine case de TabAdj et si une case est supprimé je veux que celle qui vient juste aprés elle prenne sa place, mais si je fais par exemple:

TabAdj[i]:=TabAdj[i+1];  (je crois que ça ne fera que faire pointer deux pointeurs vers le meme tableau).

voilà j'espère que c'est plus clair........merci de m'aider!
0
Guillemouze Messages postés 991 Date d'inscription samedi 25 octobre 2003 Statut Membre Dernière intervention 29 août 2013 6
6 juin 2009 à 12:40
pourquoi ne pas utiliser une TList ?

type
    TTabTest= TList;
    TPTabTest= TList {of TTabTest};
var
l : TTabTest;
l2: TPTabTest;
x: integer;
begin
l2 := TPTabTest.Create;
l := TTabTest.Create;
l.Add(Pointer(5));

l.Add(Pointer(222));

...
l2.Add(l);
...
x := Integer(TTabTest(l2[i])[j]);
0

Vous n’avez pas trouvé la réponse que vous recherchez ?

Posez votre question
f0xi Messages postés 4205 Date d'inscription samedi 16 octobre 2004 Statut Modérateur Dernière intervention 12 mars 2022 35
6 juin 2009 à 15:20
exemple de code :

const
  IntArrayCount = 10;

type
  pIntArray = ^TIntArray;
  TIntArray = packed array[0..IntArrayCount-1] of integer;

procedure IntArrayInit(const ptr: pIntArray);
begin
  FillChar(ptr^, IntArrayCount shl 2, 0);
end;

procedure IntArrayExchange(const Index1, Index2: integer; const Ptr: pIntArray);
var Tmp : integer;
begin
  Tmp := ptr^[Index2];
  ptr^[Index2] := ptr^[Index1];
  ptr^[Index1] := Tmp;
end;

function IntArrayIndexOfASC(const Value: integer; const Ptr: pIntArray): integer;
var N : integer;
begin
  result := -1;
  for N := 0 to IntArrayCount-1 do
    if Ptr^[N] = Value then
    begin
      result := N;
      break;
    end;
end;

function IntArrayIndexOfDESC(const Value: integer; const Ptr: pIntArray): integer;
var N : integer;
begin
  result := -1;
  for N := IntArrayCount-1 downto 0 do
    if Ptr^[N] = Value then
    begin
      result := N;
      break;
    end;
end;

procedure IntArrayIndexOf(const Value: integer; const Ptr: pIntArray; var Index: integer);
var N : integer;
begin
  for N := Index to IntArrayCount-1 do
    if Ptr^[N] = Value then
    begin
      Index := N;
      break;
    end;
end;

procedure IntArrayMoveUp(const Index: integer; const Ptr: pIntArray);
var Tmp : integer;
begin
  Tmp := ptr^[Index-1];
  ptr^[Index-1] := ptr^[Index];
  ptr^[Index] := Tmp;
end;

procedure IntArrayMoveDown(const Index: integer; const Ptr: pIntArray);
var Tmp : integer;
begin
  Tmp := ptr^[Index+1];
  ptr^[Index+1] := ptr^[Index];
  ptr^[Index] := Tmp;
end;

procedure IntArrayPush(const Index, Value: integer; const Ptr: pIntArray);
begin
  CopyMemory(@ptr^[Index+1], @ptr^[Index], (IntArrayCount-Index-1) shl 2);
  ptr^[Index] := value;
end;

procedure IntArrayPop(const Index: integer; const Ptr: pIntArray);
begin
  CopyMemory(@ptr^[Index], @ptr^[Index+1], (IntArrayCount-Index) shl 2);
  ptr^[IntArrayCount-1] := 0;
end;

procedure IntArrayToStrings(Strings:TStrings; const Ptr : pIntArray);
var N : integer;
begin
  Strings.BeginUpdate;
  try
    Strings.Clear;
    for N := 0 to IntArrayCount-1 do
      Strings.Add(IntToStr(ptr^[N]));
  finally
    Strings.EndUpdate;
  end;
end;

0
Samou85 Messages postés 46 Date d'inscription mardi 2 juin 2009 Statut Membre Dernière intervention 7 octobre 2009
6 juin 2009 à 22:42
OK "rt15"  si je fais comme tu le dis;  rt15 dit: "Dans ce cas faut décaler toutes les cases suivantes, pas juste celle d'après", donc à la fin du Array j'aurais la (n)éme case qui sera à la  (n-1)éme case; donc
je devrais quand meme supprimer cette (n)éme case comment le faire? 
0
Samou85 Messages postés 46 Date d'inscription mardi 2 juin 2009 Statut Membre Dernière intervention 7 octobre 2009
6 juin 2009 à 22:50
bonjour "fOxi" merci de ta réponse mais je suis débutante  et je ne vois pas lequel de ses sources est sensé etre la réponse à ma question
0
cs_rt15 Messages postés 3874 Date d'inscription mardi 8 mars 2005 Statut Modérateur Dernière intervention 7 novembre 2014 13
7 juin 2009 à 09:49
Bin après on peut se demander ce que tu appelles "supprimer" !

Array[1..10000] -> Donc ton tableau n'est pas redimensionable. Tu ne peux pas lui supprimer physiquement des cases (A l'inverse d'un tableau dynamique).

Donc il faut que tu te donnes un moyen ou un autre de connaître la dernière case occupée.
Tu as globalement deux méthodes :
1) Stocker dans un entier quelque part l'index de la dernière case occupée. Cela peut être dans une variable séparée, ou dans une case de ton tableau. Dans ton cas, un tableau de pointeur indicé de 1 à 10000, tu peux ajouter une case 0. Cette case 0, bien que Delphi considérera qu'elle contient un pointeur, tu peux mettre un Integer dedans. Suffit de caster. Mais bon c'est le genre d'astuce qui peut dérouter un(e) débutant(e). C'est la technique utilisée pour les chaîne de Delphi.
2) Mettre une valeur particulière dans la dernière case occupée. C'est la technique utilisée pour ce qu'on appelle les chaîne à zéro terminal. Elles sont très utilisées dans Windows. Cette fois, pour connaître la taille, il faut parcourir tout le tableau jusqu'à tomber sur le caractère spécial #0.

Je te propose un petit exemple basé sur la technique 1), avec un compteur dans une variable séparée (Pas dans le tableau). Et plutôt que de passer par des Integer, je vais prendre des PChar. Une liste pour afficher le contenu du tableau, un bouton pour supprimer l'élément sélectionné, un bouton pour ajouter en fin de tableau le texte d'un Edit.
unit Unit1;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls;

type
  TPTabTest= Array[1..10000] of PChar;

type
  TForm1 = class(TForm)
    lstArrayContent: TListBox;
    btnAdd: TButton;
    btnDelete: TButton;
    edtNewVal: TEdit;
    procedure FormCreate(Sender: TObject);
    procedure btnAddClick(Sender: TObject);
    procedure FormDestroy(Sender: TObject);
    procedure RefreshList;
    procedure btnDeleteClick(Sender: TObject);
  private
    lpTab: TPTabTest;
    nTabCount: Integer;
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

procedure TForm1.RefreshList;
var
  nI: Integer;
begin
  lstArrayContent.Clear;
  for nI:= 1 to nTabCount do
    lstArrayContent.AddItem(lpTab[nI], nil);
end;

procedure TForm1.FormCreate(Sender: TObject);
begin
  nTabCount:= 0;
end;

procedure TForm1.btnAddClick(Sender: TObject);
begin
  Inc(nTabCount);
  lpTab[nTabCount]:= AllocMem(256);
  lstrcpy(lpTab[nTabCount], PChar(edtNewVal.Text));
  RefreshList;
end;

procedure TForm1.FormDestroy(Sender: TObject);
var
  nI: Integer;
begin
  for nI:= 1 to nTabCount do
    FreeMem(lpTab[nI]);
end;

procedure TForm1.btnDeleteClick(Sender: TObject);
var
  nItemToDelete: Integer;   // Indice de la case à supprimer
  nI: Integer;
begin
  // Vérif qu'il y a un élément sélectionné
  if lstArrayContent.ItemIndex <> -1 then
  begin
    // Les items sont indicés à partir de 0
    nItemToDelete:= lstArrayContent.ItemIndex + 1;

    // Libération du tableau pointé
    FreeMem(lpTab[nItemToDelete]);

    // Décalage des pointeurs suivants
    for nI:= nItemToDelete to nTabCount - 1 do
      lpTab[nI]:= lpTab[nI + 1];

    // On signale que l'on a une case de moins dans le tableau
    Dec(nTabCount);

    RefreshList;
  end;
end;

end.
0
Samou85 Messages postés 46 Date d'inscription mardi 2 juin 2009 Statut Membre Dernière intervention 7 octobre 2009
13 juin 2009 à 01:20
je voudrais utiliser une ArrayList mais je ne sais pas comment la déclarer sous delphi, et si c'est la meme chose qu'une TList?
Merci de m'aider!
0
Rejoignez-nous