Konuyu Oyla:
  • Derecelendirme: 0/5 - 0 oy
  • 1
  • 2
  • 3
  • 4
  • 5
Record Üzerindeki Verilere Dinamik Erişim
#1
Merhaba,

Projem gereği her yerde kullanabileceğim bir record yapısı kuruyorum. Bu nedenle recordlar üzerinde dinamik işlemler yapmam gerekiyor. 
Başkalarınında işine yarayacağını düşünerek Linkleri Görebilmeniz İçin Üye Olmanız Gerekiyor. Üye Olabilmek İçin Lütfen Buraya Tıklayınız. konusuna ithafen, record üzerindeki verilere erişim ve value gönderme üzerine örnek kod ve proje aşağıdadır.

ADjok7.png

Linkleri Görebilmeniz İçin Üye Olmanız Gerekiyor. Üye Olabilmek İçin Lütfen Buraya Tıklayınız.

unit RecordLib;
{****************************
 RecordLib.pas 2019
 S.B
*****************************}
interface

 uses Rtti,TypInfo;

 type
   TFieldInform = record
   FieldName  : String;
   FieldType  : String;
   FieldValue : Variant;
 end;

 type
   TRecordInfo<RecordClass:record> = class
 public
   class function  GetFieldList(const ARecord:RecordClass): TArray<TFieldInform>;
   class procedure SetFieldValue(var ARecord:RecordClass;const AFieldName:String;const AValue:Variant);
 end;

implementation

{ TRecordInfo<RecordClass> }

class function TRecordInfo<RecordClass>.GetFieldList(const ARecord: RecordClass): TArray<TFieldInform>;
var
 xContext : TRttiContext;
 xType    : TRttiType;
 xField   : TRttiField;
 xCounter : Integer;
begin
 xContext := TRttiContext.Create;
 try
   SetLength(Result,Length(xContext.GetType(TypeInfo(RecordClass)).GetFields));
   xCounter := 0;
   for xField in xContext.GetType(TypeInfo(RecordClass)).GetFields do
   begin
     xType                       := xField.FieldType;
     Result[xCounter].FieldName  := xField.Name;
     Result[xCounter].FieldType  := xField.FieldType.Name;
     Result[xCounter].FieldValue := xField.GetValue(@ARecord).AsVariant;
     xCounter                    := Succ(xCounter);
   end;
 finally
   xContext.Free;
 end;
end;

class procedure TRecordInfo<RecordClass>.SetFieldValue(var ARecord:RecordClass;const AFieldName:String;const AValue:Variant);
var
 xContext : TRttiContext;
 xType    : TRttiType;
 xField   : TRttiField;
 xValue   : TValue;
begin
 xContext := TRttiContext.Create;
 try
   for xField in xContext.GetType(TypeInfo(RecordClass)).GetFields do
   begin
     xType := xField.FieldType;
     if xField.Name = AFieldName then
     begin
       case PTypeInfo(xType.Handle).Kind of
         tkInteger :
           begin
             xValue := TValue.From<Integer>(AValue);
             xField.SetValue(@ARecord,xValue);
           end;
         tkUString :
           begin
             xValue := TValue.From<String>(AValue);
             xField.SetValue(@ARecord,xValue);
           end;
         tkFloat :
           begin
             xValue := TValue.From<Double>(AValue);
             xField.SetValue(@ARecord,xValue);
           end;
       end;
     end;
   end;
 finally
   xContext.Free;
 end;
end;

end.

Örnek

  type
   TTestRecord = record
   VAL_STR : String;
   VAL_INT : Integer;
   VAL_DTE : TDateTime;
   VAL_FLT : Double;
 end;

procedure TFrmTestRecord.BtnOKClick(Sender: TObject);
Var
 xTestRecord : TTestRecord;
 xFieldArray : TArray<TFieldInform>;
 Ind         : Integer;
begin
 memDefault.Clear;
 memNew.Clear;

 xTestRecord.VAL_STR := 'Test1';
 xTestRecord.VAL_INT := 1;
 xTestRecord.VAL_DTE := StrToDateTime('01.01.2019 01:10:15');
 xTestRecord.VAL_FLT := 0.1;

 xFieldArray := TRecordInfo<TTestRecord>.GetFieldList(xTestRecord);
 for Ind := Low(xFieldArray) to High(xFieldArray) do
     memDefault.Lines.Add
     (
       Format('FieldName[%s] -- FieldType[%s] -- Value=%s',
       [
         xFieldArray[Ind].FieldName
         ,xFieldArray[Ind].FieldType
         ,VarToStr(xFieldArray[Ind].FieldValue)
       ]
       )
     );

 TRecordInfo<TTestRecord>.SetFieldValue(xTestRecord,'VAL_STR','Test2');
 TRecordInfo<TTestRecord>.SetFieldValue(xTestRecord,'VAL_INT',2);
 TRecordInfo<TTestRecord>.SetFieldValue(xTestRecord,'VAL_DTE',Now);
 TRecordInfo<TTestRecord>.SetFieldValue(xTestRecord,'VAL_FLT',0.2);

 xFieldArray := TRecordInfo<TTestRecord>.GetFieldList(xTestRecord);
 for Ind := Low(xFieldArray) to High(xFieldArray) do
     memNew.Lines.Add
     (
       Format('FieldName[%s] -- FieldType[%s] -- Value=%s',
       [
         xFieldArray[Ind].FieldName
         ,xFieldArray[Ind].FieldType
         ,VarToStr(xFieldArray[Ind].FieldValue)
       ]
       )
     );
end;
Yalnızım ama bir kente yürüyen ordu gibiyim, edebiyattan kaçınmalıyım..
Cevapla


Konu ile Alakalı Benzer Konular
Konular Yazar Yorumlar Okunma Son Yorum
  Offset Kavramı ve Dinamik Dizi Yapımı ismailkocacan 14 1.816 07-11-2018, Saat: 08:47
Son Yorum: Tuğrul HELVACI



Konuyu Okuyanlar: 1 Ziyaretçi