المشاركات : 306
المواضيع 45
:
: 0
الإنتساب : Jul 2012
إقتباس :ستحتاج الى أن تكون على علم بالتقنيات التالية :
- Generics & Collections
- OOP
- RTTI
خذلك أولا قهوة ثقيلة ..
ثم توكل على الله ..
ثم اطلع على هذا الرابط :
هذه تريد ليلة من ليال الشتاء الطويلة

الف شكر لك وعلى تعاونك
--------------------------------------
إقتباس :السلام عليكم
عندما تقوم بانشاء اوبجكت من كلاس فان هدا الأبجكت يشغل مساحة من الداكرة ولنسخ الأوبجكت يكفي معرفة المساحة التي يشغلها انظر المثال كتبته بشكل سريع
فعلاً هذه كانت نظرتي وتوقعي للامر
لكن فكرت بالامر أكثر وتذكرت ان وبجكت يمكن ان يحتوي على على اوبجكت آخر
مثال عملي :
PHP كود :
type
TMyClass = Class
Name: string; // in your way .. this value will be copied fine because it's value
Age: integer; // same here
Address: string;
PhoneNumbers: TStringList; // this will be the problem .. when you copy it you just copy the pointer for it
// so if the obj1 Freed the obj2 will lose its PhoneNumbers pointer because it
// belong to obj1
end;
فإذا اردت ان اقوم بنسخ حقيقي سيتطلب الامر ان اعرف عنوان الوبجكت الذي أريـ ـد نسخه ثم اقوم بنسخ للذاكرة الاوبجكت
وبعد ذلك اتأكد هل البيانات التي تم نسخها هي قيم(Values) ام مؤشرات(Pointers) إذا كانت مؤشرات
اقوم بنسخ المكان الذي يشير إليه هذا المؤشر ثم أتاكد من البيانات التي نسختها هل تشير إلى مؤشرات آخرى ام لا ...وعلى هذا المنوال الغير محكم فربما تحدث اخطا ..إلخ
طبعاً كل هذه هي توقعات نظرية ولم اطبق اين منها
المشاركات : 306
المواضيع 45
:
: 0
الإنتساب : Jul 2012
فعلاً كما توقعت
انظر لهذا المثال الذي قمت بتطبيق فكرتك فيه
PHP كود :
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs;
type
TForm1 = class(TForm)
procedure FormCreate(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
TMyClass = class
private
public
Name: String;
Age: Integer;
PhoneNumbers: TStringList;
constructor Create; virtual;
destructor Destroy; override;
end;
var
Form1: TForm1;
obj1, obj2: TMyClass;
implementation
{$R *.dfm}
procedure TForm1.FormCreate(Sender: TObject);
begin
obj1 := TMyClass.Create;
obj1.Name := 'Ali';
obj1.Age := 15;
obj1.PhoneNumbers.Add('XXXXXXXXXXXXXXXXX');
ShowMessage( Format('Pointer for obj1.PhoneNumbers is : %p', [Pointer(obj1.PhoneNumbers)])
+ ' fist number value is : ' + obj1.PhoneNumbers.Strings[0]);
obj2 := TMyClass.Create;
ShowMessage(IntToStr(obj1.InstanceSize));
CopyMemory(Pointer(obj2), Pointer(obj1), obj1.InstanceSize);
obj1.Free;
// here you will get the error.. Because there is no pointer anymore
ShowMessage('fist number value is : ' + obj2.PhoneNumbers.Strings[0]);
obj2.Free;
end;
{ TMyClass }
constructor TMyClass.Create;
begin
PhoneNumbers := TStringList.Create;
end;
destructor TMyClass.Destroy;
begin
FreeAndNil(PhoneNumbers);
inherited;
end;
end.
المشاركات : 632
المواضيع 66
:
: 6
الإنتساب : Jul 2010
me_delphi كتب :السلام عليكم
عندما تقوم بانشاء اوبجكت من كلاس فان هدا الأبجكت يشغل مساحة من الداكرة ولنسخ الأوبجكت يكفي معرفة المساحة التي يشغلها انظر المثال كتبته بشكل سريع
يا ريت الطريقة كانت بتلك البساطة ..
جرب هذا الكود :
PHP كود :
var
obj1, obj2: Tmycls;
begin
obj1 := Tmycls.Create();
obj2 := Tmycls.Create();
obj1.clonCedsit('jamalcoder');
obj1.FName := 'test';
CopyMemory(Pointer(obj2), Pointer(obj1), obj1.InstanceSize);
obj1.FName :='nil';
Self.Caption := obj2.FName; // failed !
obj1.Free;
obj2.Free;
end;
Open Your Source .. Open Your Mind
المشاركات : 358
المواضيع 34
:
: 2
الإنتساب : Nov 2008
نعم الأمر معقد..انا لم أقم بالتجريب اتبعت المنطق فقط لكن العملية تتطلب دراسة و فهم
المهم هدا الكود لم يعمل لنه تم تعديل الأوبجكت 1 أي يجب ان تكون هده العملية هي الأخيرة
إقتباس :copymemory(pointer(obj2), pointer(obj1), obj1.instancesize);
والا لن يكون الأوبجكت 1 و 2 متساويين
أي يجب ان ننتهي من جميع التعديلات قبل أن نقوم بعملية النسخ
لا اله الا أنت سبحانك اني كنت من الضالمين
المشاركات : 306
المواضيع 45
:
: 0
الإنتساب : Jul 2012
نفس النتيجة
عندما اعدل الـ
obj1.PhoneNumbers
سيتم تغيير قيمة الـ obj2.PhoneNumbers
PHP كود :
obj1 := TMyClass.Create;
obj1.PhoneNumbers.strings[0] := '000000';
obj2 := TMyClass.Create;
copymemory(pointer(obj2), pointer(obj1), obj1.instancesize);
showMessage(obj1.PhoneNumbers.strings[0]); { Result will be : 000000 }
showMessage(obj2.PhoneNumbers.strings[0]); { Result will be : 000000 }
obj1.PhoneNumbers.strings[0] := '555555';
showMessage(obj1.PhoneNumbers.strings[0]); { Result will be : 555555}
showMessage(obj2.PhoneNumbers.strings[0]); { Result will be : 555555}
// so obj2 use same TStringList that belong to obj1 .. if you change PhoneNumbers
// in obj1 it will change in obj2.. same if you change obj2.PhoneNumbers it will change
// in obj1
والمطلوب هو نسخ الكلاس أي يكون الـ obj2 يملك مساحته الخاصة بالذاكرة والقيم الخاصة به بالذاكرة حيث انه ليس مرتبط بالـ obj1 كلياً