Форум: "Прочее";
Текущий архив: 2016.07.24;
Скачать: [xml.tar.bz2];
ВнизRecord -> String Найти похожие ветки
← →
K-1000 © (2015-10-20 10:48) [0]Всем привет.
Можно ли с помощью RTTI (D7) любую структуру перевести в строку?
var
PenData: TPenData;
begin
Label1.Caption:= RecordToString(PenData);
end;
← →
Sha © (2015-10-20 10:56) [1]нельзя
← →
virex(home) © (2015-10-20 11:30) [2]в delphi7 структура не является классом, в отличие от c# и java где все (?) примитивы имеют обертки-классы, позволяющие сделать что-то типа PenData.ToString()
з.ы. мысли вслух
← →
Юрий Зотов © (2015-10-20 13:29) [3]Насколько помню, в D7 RTTI для record"ов не генерируется. Значит - нельзя.
← →
DVM © (2015-10-20 13:38) [4]
> K-1000 © (20.10.15 10:48)
> Можно ли с помощью RTTI (D7) любую структуру перевести в
> строку?
Ты же как правило с определенными структурами работаешь. И их скорее всего небольшое количество. Что мешает написать для них функции?
← →
Юрий Зотов © (2015-10-20 13:40) [5]Но можно представить в виде HEX-строки память, которую занимает запись. Если, конечно, в ней нет ссылочных полей.
← →
K-1000 © (2015-10-20 14:26) [6]
> Sha © (20.10.15 10:56) [1]
>
> нельзя
А в новых Дельфи?
>virex(home) © (20.10.15 11:30) [2]
>в delphi7 структура не является классом, в отличие от c# и java где все (?) >примитивы имеют обертки-классы, позволяющие сделать что-то типа >PenData.ToString()
>з.ы. мысли вслух
RTTI может энум TBrushStyle перевести в строку.
Который не является TObject"ом.
> DVM © (20.10.15 13:38) [4]
> Ты же как правило с определенными структурами работаешь. И их скорее
> всего небольшое количество. Что мешает написать для них функции?
Так и делаю пока. Но у многих API есть длиннющие и загадочные структуры как TDeviceMode или Директовские структуры, в которых нужно посмотреть нужные поля, а желательно все.
> Юрий Зотов © (20.10.15 13:40) [5]
>
> Но можно представить в виде HEX-строки память, которую занимает
> запись. Если, конечно, в ней нет ссылочных полей.
Можно поподробнее?
← →
Sha © (2015-10-20 14:57) [7]BinToHex, HexToBin
← →
Kerk © (2015-10-20 15:13) [8]
> K-1000 © (20.10.15 14:26) [6]
>
> > Sha © (20.10.15 10:56) [1]
> >
> > нельзя
>
> А в новых Дельфи?
В новых можно
http://stackoverflow.com/a/23824290
← →
Юрий Зотов © (2015-10-20 16:36) [9]Ниже - еще один велосипед (чтобы совсем уж не забыть Delphi).
Писал навскидку, возможны ошибки.
const
HexDigits: array[0..$F] of char =
("0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "A", "B", "C", "D", "E", "F");
function MemoryAsHexString(p: PByte, size: integer): AnsiString;
var
i: integer;
t: byte;
begin
SetLength(Result, size * 2);
for i := 0 to (size - 1) do
begin
t := p^ shr 4;
Result[2 * i + 1] = HexDigits[t];
t := p^ and $F;
Result[2 * i + 2] = HexDigits[t];
inc(p);
end
end;
// Пример вызова:
var
AnyRecord = record // здесь лучше, но не обязательно: packed record
... // здесь не должно быть ссылочных полей
end;
MemoryAsHexString(PByte(@MyRecord), SizeOf(MyRecord));
← →
K-1000 © (2015-10-20 19:42) [10]
> Kerk © (20.10.15 15:13) [8]
>
>
> > K-1000 © (20.10.15 14:26) [6]
> >
> > > Sha © (20.10.15 10:56) [1]
> > >
> > > нельзя
> >
> > А в новых Дельфи?
>
> В новых можно
> http://stackoverflow.com/a/23824290
С Delphi XE 2?
← →
Германн © (2015-10-21 01:12) [11]
> Но у многих API есть длиннющие и загадочные структуры
И при чём тут RTTI?
← →
K-1000 © (2015-10-21 20:04) [12]
> Германн © (21.10.15 01:12) [11]
>
>
> > Но у многих API есть длиннющие и загадочные структуры
>
> И при чём тут RTTI?
>
Чтобы RTTI мне помог такие структуры переводить в строку.
← →
Kerk © (2015-10-21 20:42) [13]
> K-1000 © (20.10.15 19:42) [10]
>
> С Delphi XE 2?
С Delphi 2010, если я не ошибаюсь.
← →
Германн © (2015-10-22 00:31) [14]
> K-1000 © (21.10.15 20:04) [12]
>
>
> > Германн © (21.10.15 01:12) [11]
> >
> >
> > > Но у многих API есть длиннющие и загадочные структуры
> >
> > И при чём тут RTTI?
> >
>
>
> Чтобы RTTI мне помог такие структуры переводить в строку.
>
RTTI есть только у Дельфийских классов. Ну т.е. то RTTI, которое тебе доступно в Дельфийской программе. Откуда она возьмётся в некоем стороннем API?
← →
Кто б сомневался © (2015-10-22 03:21) [15]
> Чтобы RTTI мне помог такие структуры переводить в строку.
Строка это тоже структура, но одного вида, а твоя структура другого вида. Чтобы все работало, нужно описать что, как и куда превращать.
Короче это можно сделать через перегруженные операторы - operator overloading (не помню когда они появились, может и в Delphi ЧУ2), после этого можно делать так:var
PenData: TPenData;
begin
Label1.Caption:= PenData;
// и наборот
PenData := Label1.Caption;
end;
TString256 = record // это любая структура
fArrayChr : array [0..255] of char;
class operator Implicit(const aRec: TString256): string; // переводим структуру в строку
class operator Implicit(const aStr: string): TString256; // и строку в свою структуру
end;
class operator TString256.Implicit(const aStr: string): TString256;
begin
DoImplicit(aStr, @Result.fArrayChr[0], SizeOf(Result.fArrayChr));
end;
class operator TString256.Implicit(const aRec: TString256): string;
begin
Result := aRec.fArrayChr;
end;
procedure DoImplicit(const aStr: string; aBuf: Pointer; aSize: integer);
const
FMT_MSG = "Implicit overloading error. Buf size: %d, String Size: %d";
var
vSize: integer;
begin
ZeroMemory(ABuf, aSize);
if Length(aStr) = 0 then exit;
vSize := Length(aStr) * SizeOf(Char);
//Assert(vSize <= aSize, Format(FMT_MSG, [aSize div 2, vSize]));
if vSize > aSize then
vSize := aSize;
Move(aStr[1], ABuf^, vSize);
end;
DoImplicit не нужно делать отдельной процедурой, просто кусок из кода выдрал.
← →
K-1000 © (2015-10-22 15:36) [16]
> Германн © (22.10.15 00:31) [14]
> RTTI есть только у Дельфийских классов. Ну т.е. то RTTI,
> которое тебе доступно в Дельфийской программе. Откуда она
> возьмётся в некоем стороннем API?
Мне нужно конвертировать длинные структуры какого угодно API, будь это WinAPI, OGGVORBIS или DX.
> Кто б сомневался © (22.10.15 03:21) [15]
Мммм... Не понятно это код может перевести допустим структуру
Windows.TDeviceModeA в строку.
← →
Игорь Шевченко © (2015-10-22 16:20) [17]
> Мне нужно конвертировать длинные структуры какого угодно
> API, будь это WinAPI, OGGVORBIS или DX.
Стесняюсь спросить, с какой целью ?
← →
Юрий Зотов © (2015-10-22 17:32) [18]> Игорь Шевченко © (22.10.15 16:20) [17]
+1. Похоже на X, Y, Z.
← →
Кто б сомневался © (2015-10-22 18:07) [19]
> K-1000 © (22.10.15 15:36) [16]
>
>
> Мне нужно конвертировать длинные структуры какого угодно
> API, будь это WinAPI, OGGVORBIS или DX.
Ах вон оно чё.
На этом этапе вы заходите в потайной мир программистов, вы наверное непосвященный пока. Здесь такое дело - не все можно рассказывать на форумах.
Рассказав и показав вам в подробностях как скопировать любую структуру API в строку - таким образом публично откроются секретные лазейки, при помощи которых можно потенциально взломать Винду и вообще любую прогу в ней.
И поэтому любой хороший программист будет спрашивать с какой целью вы это собираетесь делать, - так требует правила тайного культа, - что вы на стороне добра и не хакер случайно вдруг.
← →
Andy BitOff © (2015-10-22 19:22) [20]
> и не хакер случайно вдруг.
Свят, свят, свят. Упаси нас бог.
← →
K-1000 © (2015-10-22 19:37) [21]
> Игорь Шевченко © (22.10.15 16:20) [17]
>
>
> > Мне нужно конвертировать длинные структуры какого угодно
> > API, будь это WinAPI, OGGVORBIS или DX.
>
>
> Стесняюсь спросить, с какой целью ?
С той же, что и вопрос со СтэкОферфлоу:
"access all elements of a record using RTTI".
Бывает так, что некоторые поля структуры не ясно что содержат.
Даже читая MSDN не ясно, что именно будет в поле.
Тот же MSDN допустим утверждает, что поле TDisplayDeviceA.DeviceId -
Not used. А если посмотреть самому, то это поле возвращает нужные данные.
Как бы я это узнал, если бы не сделал полную конвертацию структуры в строку? Никак.
Ещё у многих API есть море длиннющих структур, хочется в поисках доп. информации или ради простого любопытства посмотреть "А что там?".
Тем более некоторые структуры имеют плохую документацию. Или структура является вообще недокументированной. (Привет, мастеру Rouse_)
Писать для каждой структуры свою функцию конвертирования в строку...
Нудно. Можно конечно сделать простой парсер текстового представления структуры... Но как ясно из ветки, с этим может справиться нынешний RTTI.
Да и вопрос скорее ради "А может ли Delphi". Как вижу, может.
← →
Кто б сомневался © (2015-10-22 20:07) [22][21]
> Тот же MSDN допустим утверждает, что поле TDisplayDeviceA.
> DeviceId -
> Not used. А если посмотреть самому, то это поле возвращает
> нужные данные.
> Как бы я это узнал, если бы не сделал полную конвертацию
> структуры в строку? Никак.
>
Zenais, futuebam matrem tuam!
Извините за мой латинский.
Чтобы посмотреть что в структуре, нужно поставить точку остановки (breakpoint) - в том месте где она используется. Потом запустить прогу в отладчике Delphi - и когда остановится на этой точке - навести курсор на эту структуру (переменную) и нажать Ctrl + Shift + Клик левой мышью.
Так можно посмотреть любую переменную.
Появиться окошко ,которое покажет все содержимое структуры, разбитое по названиями - значениям итд.
И можно дальше трассировать и значения будут меняться в этом окошке.
← →
Юрий Зотов © (2015-10-22 22:06) [23]> Появиться окошко ,которое покажет все содержимое структуры,
> разбитое по названиями - значениям итд.
Причем эти данные можно будет смотреть уже с учетом порядка хранения байт в памяти. Чего не покажет строка.
← →
Юрий Зотов © (2015-10-23 05:29) [24]> K-1000 © (20.10.15 10:48)
> Можно ли с помощью RTTI (D7) любую структуру перевести в строку?
Почему бы было не задать изначальный вопрос? Например: "как увидеть содержимое структуры?".
Типичное X, Y, Z: http://www.gunsmoker.ru/2008/10/x-y-z.html
← →
K-1000 © (2015-10-25 15:54) [25]
> Кто б сомневался © (22.10.15 20:07) [22]
>
> [21]
Отладчиком ещё не пользовался. :)
> Юрий Зотов © (23.10.15 05:29) [24]
>
> > K-1000 © (20.10.15 10:48)
> > Можно ли с помощью RTTI (D7) любую структуру перевести
> в строку?
>
> Почему бы было не задать изначальный вопрос? Например: "как
> увидеть содержимое структуры?".
>
> Типичное X, Y, Z: http://www.gunsmoker.ru/2008/10/x-y-z.
> html
Ну не знал я, что можно увидеть структуру не в виде строки.
← →
Юрий Зотов © (2015-10-25 20:06) [26]> K-1000 © (25.10.15 15:54) [25]
Это нормально. Каждый из нас чего-нибудь не знает. Даже самые-самые просветленные из просветленных.
:o)
На будущее - старайтесь задавать именно тот вопрос, который относится к изначальной проблеме. Тогда ответ будет и более быстрым, и более точным.
Кстати. Пусть поле структуры - это 4-х байтовое беззнаковое целое 875770417. В 16-ричном виде это число равно $34333231, но на платформе Х86/32 в памяти будет записано $31323334 (такова особенность платформы).
В итоге - при просмотре в виде ANSI-строки увидим совсем другое "число": 1234. Для получения "правильного" числа потребуются ручные преобразования (в которых, к тому же, легко ошибиться). А при просмотре отладчиком можно указать нужный режим - и все преобразования будут сделаны автоматически.
← →
Кто б сомневался © (2015-10-28 15:11) [27]
> Юрий Зотов © (25.10.15 20:06) [26]
+1
Еще момент, а то как оказалось некоторые (многие?) этого не знают. Помню когда работал в одной компании, мне сказали не использовать record"ы, а использовать классы вместо них, пришлось объяснять.
Структура (в Delphi - record) - это трафарет для куска памяти. Есть кусок памяти размером в 10 байт.
И на него можно "положить" разные трафареты, которые будут давать разные значения, в зависимости от размеров полей в структуре.
Любую структуру можно скопировать куда угодно c помощью Move - просто копируем один кусок памяти в другой (например в строку, только при исп. Move нужно заранее выделить память для строки SetLength).
← →
Кто б сомневался © (2015-10-28 15:22) [28]Так вот, вся проблема при копировании одного в другое - это интерпретация этих данных - т.е. как их читать потом юзеру.
В строке string они будут выглядеть по другому - т.к. у строки один символ (char) = 1 байт, а с Delphi 2009 один char в string = 2 байта (т.к. юникод) + там ньюансы с Pchar текстом - обычно в структурах дают адрес на кусок текста "где-то там в памяти" - поэтому текст в строку string не попадет, а только его адрес ну и др.
И кстати переходи с Dephi 7 на более новую. Там реально удобнее. На XE5 например или выше. И программы быстрее работают, т.к. используют сразу юникод версии функций Win API, без предварительной конвертации (в Windows, ANSI функции сначала конвертируются в юникод (самой Виндой, тут Delphi не причем), а потом вызываются).
← →
Кто б сомневался © (2015-10-28 15:39) [29]
> Есть кусок памяти размером в 10 байт.
Это для примера конечно же, размер структуры (куска памяти с которого читаем) может быть любой
← →
Кто б сомневался © (2015-10-28 16:01) [30]
> т.к. у строки один символ (char) = 1 байт, а с Delphi 2009
> один char в string = 2 байта (т.к. юникод) +
integer например = 4 байтам. Pointer тоже = 4 (в x64 версии = 8 байтам).
Поэтому при просмотре строки как текста, она будет показана юзеру как набор однобайтных Char ов (если ANSI string). Например если напрямую перекинуть (Move) какое то число хранящееся в integer (4 байта), то оно будет "разбросано" (интерпретировано как) на 4 символа char (char = 1 байту), будет 4 разных числа.
И это не какая-то особенность Delphi, а техническая особенность, которая есть во всех нативных языках и платформах.
Чтобы узнать размер структуры - SizeOf().
← →
K-1000 © (2015-10-28 16:30) [31]
> Кто б сомневался © (28.10.15 15:22) [28]
> И кстати переходи с Dephi 7 на более новую. Там реально
> удобнее. На XE5 например или выше. И программы быстрее работают,
> т.к. используют сразу юникод версии функций Win API, без
> предварительной конвертации (в Windows, ANSI функции сначала
> конвертируются в юникод (самой Виндой, тут Delphi не причем),
> а потом вызываются).
>
Да вот устанавливаю "Delphi 10 Seattle Lite".
Думаю меня ждёт "лёгкий шок" после "Delphi 7" 2002-го выпуска. :)
← →
Юрий Зотов © (2015-10-28 19:57) [32]> Структура (в Delphi - record) - это трафарет для куска памяти.
>
> разные трафареты ... будут давать разные значения
>
> вся проблема ... интерпретация этих данных
То же самое относится и к любой другой переменной, а не только к вариантной записи. См. absolute.
Страницы: 1 вся ветка
Форум: "Прочее";
Текущий архив: 2016.07.24;
Скачать: [xml.tar.bz2];
Память: 0.55 MB
Время: 0.006 c