سؤال

أريد تمرير وسيطات التنسيق Args في الشكل وظيفة.لقد وجدت بعض الأمثلة على ذلك ، ولكن لا أستطيع معرفة كيفية تعيين ثابت سلسلة في تفاريك عضو.فشل التعليمات البرمجية التالية على تجميع مع E2089 Invalid typecast.

procedure TForm1.Button1Click(Sender: TObject);
var Arguments: array of TVarRec;
begin
  SetLength(Arguments, 2);

  Arguments[0].VInteger := 111;
  Arguments[1].VAnsiString :=  PAnsiString('Text'); // I want to set this member

  ShowMessage(Format('Decimal: %d, String: %s', Arguments));
end;

يمكن لأي شخص أن يقترح لي كيفية تعيين سلسلة (أو أنسيسترينغ) ثابت إلى عضو تفاريك ?أنا باستخدام دلفي 2009.

شكرا جزيلا

هل كانت مفيدة؟

المحلول

ويبدو أن هذا العمل في ز:

var
  Args: array[0..1] of TVarRec;
  S: AnsiString;
  U: UnicodeString;
begin
  S := 'Hello';
  U := 'world';
  Args[0].VType := vtAnsiString;
  Args[0].VAnsiString := Pointer(S);
  Args[1].VType := vtUnicodeString;
  Args[1].VUnicodeString := Pointer(U);

  Writeln(Format('%s, %s!', Args));
end;

نصائح أخرى

فقط بلدي اثنين سنتا.إجابة توندريج صحيحة ، لكنني أردت فقط التأكيد على بعض النقاط.والتعليقات ليست مكانا جيدا للقيام بذلك.

يرجى أن يكون على علم بأن AnsiString يجب الرجوع إليها خلال كل الوقت TVarRec سيتم استخدامها.

على سبيل المثال ، إذا قمت بكتابة وظيفة إعداد مجموعة من TVarRec, ، يجب عليك التأكد من أنك قمت بعمل نسخة مؤقتة من AnsiString تم إنشاؤه داخل الوظيفة إلى متغير سيبقى حتى كل الوقت TVarRec يتم استخدام مجموعة.وإلا قد يكون لديك بعض انتهاك الوصول العشوائي (وليس في كل مرة ، ولكن فقط عندما مم إعادة تعيين ansistring الذاكرة).

على سبيل المثال ، الكود التالي هو غير صحيح:

type
  TVarRec2 = array[0..1] of TVarRec;

procedure SetVarRec(a,b: integer; var Result: TVarRec2);
begin
  Result[0].VType := vtAnsiString;
  Result[0].VString := pointer(AnsiString(IntToStr(a)));
  Result[1].VType := vtUnicodeString;
  Result[1].VString := pointer(UnicodeString(IntToStr(b)));
end;

لأن AnsiString و UnicodeString سيتم تحرير المتغيرات المؤقتة عند انتهاء الإجراء ، و Results[].VString سوف لا تزال تشير إلى تلك الذاكرة المحررة...

باستخدام فئة أو سجل مع بعض سلسلة خاصة مؤقتة قد تفعل خدعة:

type
  TMyVar2 = record
  private
    tmpA: AnsiString;
    tmpB: UnicodeString; 
  public
    VarRec: TVarRec2;
    procedure SetVarRec(a,b: integer);
  end;

procedure TMyVar2.SetVarRec(a,b: integer);
begin
  VarRec[0].VType := vtAnsiString;
  tmpA := AnsiString(IntToStr(a));
  VarRec[0].VString := pointer(tmpA);
  VarRec[1].VType := vtUnicodeString;
  tmpB := UnicodeString(IntToStr(b));
  VarRec[1].VString := pointer(tmpB);
end;

بالطبع ، في البرنامج الخاص بك قد يكون لديك فئة موجودة بالفعل.في هذه الحالة ، من الأفضل استخدام طريقة وبعض السلاسل المؤقتة الخاصة.لكي تكون الطريقة آمنة متعددة الخيوط (أي.إعادة المشارك) يجب عليك تقديم السلاسل المؤقتة كمعلمات...

أستخدم هذه الخدعة للحصول على مجموعة ديناميكية صالحة من TVarData تحتوي على بعض AnsiString المحتوى في فئة.في الواقع, TVarData و TVarRec كلاهما يستخدم هذا المؤشر غير المشار إليه للسلاسل ، والتي يمكن أن تكون مربكة.

كن على علم بأن القضايا التي تنطوي على pointer(S) مثل البيانات يمكن أن يكون من الصعب تتبع.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top