Адрес переменной по имени

Вопросы программирования на Free Pascal, использования компилятора и утилит.

Модератор: Модераторы

Адрес переменной по имени

Сообщение Stargazer » 30.11.2006 20:24:21

Всем привет!
Битый час ковыряюсь, не могу найти, как определить адрес переменной модуля. Как вариант, сошло бы и определение адреса поля класса TObject.FieldAddress, но оно не работает! MethodAddress, при всё при этом, прекрасно отрабатывает.

Где собака порылась?
Stargazer
новенький
 
Сообщения: 52
Зарегистрирован: 30.05.2005 09:46:32

Сообщение shade » 30.11.2006 22:01:58

@myvar или addr(myvar)
для поля @obj.field или addr(obj.field)

В чем проблема??
Аватара пользователя
shade
энтузиаст
 
Сообщения: 879
Зарегистрирован: 21.02.2006 20:15:48
Откуда: http://shamangrad.net/

Сообщение Stargazer » 30.11.2006 22:15:35

Разве @ и addr не одно и то же? Хотя не суть, мне нужно по имени переменной определить её адрес, в рантайме, естественно.
Определение адреса метода по его имени работает нормально.
Stargazer
новенький
 
Сообщения: 52
Зарегистрирован: 30.05.2005 09:46:32

Сообщение Stargazer » 01.12.2006 11:10:07

И, кстати, "вы будете смеяться", но пример из дистрибутива FPC тоже не работает! Вот полный код (правда, я его немного поредактировал, т.к. не нашёл модуля rttiobj, в котором должен быть объявлен TMyTestObject):

Код: Выделить всё
program demo;
{ This program demonstrates the GetStrProp function }

{.$mode objfpc}
{$mode delphi}
{$TYPEINFO+}

uses typinfo;

type
    TMyTestObject = class
    private
           s : string;
    public
    property AnsiStringField : string read s write s;
    end;

Var
  O : TMyTestObject;
  PI : PPropInfo;

begin
  O:=TMyTestObject.Create;
  O.AnsiStringField := 'hello';
  PI:=GetPropInfo(O,'AnsiStringField');
  Writeln('String property : ');
  Writeln('Value                   : ',O.AnsiStringField);

// при попытке вызвать GetStrProp выскакивает исключение с названием "Unknown Property"!

  Writeln('Get (name)              : ',GetStrProp(O,'AnsiStringField'));
  Writeln('Get (propinfo)          : ',GetStrProp(O,PI));
  SetStrProp(O,'AnsiStringField','First');
  Writeln('Set (name,''First'')      : ',O.AnsiStringField);
  SetStrProp(O,PI,'Second');
  Writeln('Set (propinfo,''Second'') : ',O.AnsiStringField);
  O.Free;
end.


p.s. FPC 2.0.4
Stargazer
новенький
 
Сообщения: 52
Зарегистрирован: 30.05.2005 09:46:32

Сообщение Stargazer » 01.12.2006 11:27:47

Блин, вот что значит, вслух произнести проблему.
Если property объявлена как published, то всё работает.
Так что вопрос снимается!
Хы, а FieldAddress так и не возвращает адрес.

Код: Выделить всё
O.FieldAddress('AnsiStringField');


Хоть поле ему подставляй, хоть пропертю. Ну ладно, хоть GetStrProp работает, и на том спасибо :)
Stargazer
новенький
 
Сообщения: 52
Зарегистрирован: 30.05.2005 09:46:32

Сообщение Mirage » 06.12.2006 23:22:59

FieldAddress должно работать только с published свойствами.
Mirage
энтузиаст
 
Сообщения: 881
Зарегистрирован: 06.05.2005 20:29:07
Откуда: Russia

Сообщение Stargazer » 09.12.2006 23:01:15

Ага, вот я и нашёл неувязочку!

В доке, и впрямь написано - для published полей генерируется типовая информация для рантайма. Но! Согласно тому же мануалу, эти поля должны иметь тип класса. И действительно, при попытке объявить любую переменную в разделе published, компилер ругается.

Хотя в описании метода TObject.FieldAddress и не сказано, что это самое field может быть любого типа.

Вот такая заковыка.
Stargazer
новенький
 
Сообщения: 52
Зарегистрирован: 30.05.2005 09:46:32

Сообщение Stargazer » 19.12.2006 11:03:26

Вот ещё над чем я призадумался.
С запуском метода, определенного по имени с помощью MethodAddress, я разобрался. Но теперь и этого мало :)
Хочется передавать параметры в этот метод :)
Это уж совсем шаманство, да?
Stargazer
новенький
 
Сообщения: 52
Зарегистрирован: 30.05.2005 09:46:32

Сообщение Stargazer » 19.12.2006 14:17:03

Stargazer писал(а):Вот ещё над чем я призадумался.
С запуском метода, определенного по имени с помощью MethodAddress, я разобрался. Но теперь и этого мало :)
Хочется передавать параметры в этот метод :)
Это уж совсем шаманство, да?


Сам себе отвечаю:
http://forum.vingrad.ru/index.php?act=m ... num=000278

В принципе, ничего сложного, надо только один раз увидеть, как это делается.

На всякий случай, процитирую:
Код: Выделить всё
... }
type
  PYourMethod = ^TYourMethod;
  TYourMethod = procedure(S: string) of Object;


procedure TMainForm.Button1Click(Sender: TObject);
begin
  ExecMethodByName('SomeMethod');
end;


procedure TMainForm.ExecMethodByName(AName: string);
var
  PAddr: PYourMethod;
  M: TMethod;
begin
  PAddr := MethodAddress(AName);
  if PAddr <> nil then
  begin
    M.Code := PAddr;
    M.Data := Self;
    TYourMethod(M)('hello');
  end;
end;


procedure TMainForm.SomeMethod(S: string);
begin
  ShowMessage(S);
end;
Stargazer
новенький
 
Сообщения: 52
Зарегистрирован: 30.05.2005 09:46:32


Вернуться в Free Pascal Compiler

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 89

Рейтинг@Mail.ru