A little study on the way Delphi parameter transmission mode

xiaoxiao2021-03-06  86

Something D6DG says that the default parameter transfer mode will consume additional memory because it will generate a local copy for the variable, and the const method optimizes the memory occupation of the parameter passing of the string and the record type. Thus guessing the parameters passing of the const method is also transmitted by address, just the compiler forced the code to modify the change in the CONST mode. In order to confirm my guess, the following experiments are designed, and the strings are used in this experiment (the strings mentioned herein refer to the reference count in the internal structure of the Delphi default string ANSISTRING). Regarding the reference count of strings, combined with the actual research in D6DG, it is concluded that the string address is actually the address of the first character of its content, and the 12-byte memory before this address. The content is the head in the internal structure of the string, which is the 32-bit string occupied by the content space size, 32-bit reference count, 32-bit string length (only in Delphi 7, speculating Delphi 7 previous 32 digits The string structure in Delphi should be like this, not verified).

SGLOBAL is global string variable in the following code. Procedure Method1 (S: String);

VAR

P: pinteger;

Begin

// s: = s 'k';

// The string is actually a pointer, but it is only forced to convert it to Pinteger standby.

P: = pinteger (s);

// Get the address of the string address left offset 8 bytes, which is the location of the 32-bit reference count of the string.

P: = Pinteger (Integer (P) - 8);

Form1.Memo1.Lines.Add ('s reference count:' INTOSTR (P ^));

P: = Pinteger (SGLOBAL);

P: = Pinteger (Integer (P) - 8);

Form1.Memo1.Lines.Add ('sglobal reference count:' INTOSTR (P ^));

Form1.Memo1.Lines.Add ('s address:' INTOSTR (Integer (Pointer (S))))

Form1.Memo1.Lines.Add ('');

END;

Procedure Method2 (var s: string);

VAR

P: pinteger;

Begin

P: = pinteger (s);

P: = Pinteger (Integer (P) - 8);

Form1.Memo1.Lines.Add ('s reference count:' INTOSTR (P ^));

P: = Pinteger (SGLOBAL);

P: = Pinteger (Integer (P) - 8);

Form1.Memo1.Lines.Add ('sglobal reference count:' INTOSTR (P ^));

Form1.Memo1.Lines.Add ('s address:' INTOSTR (Integer (Pointer (S))))

Form1.Memo1.Lines.Add ('');

END;

Procedure Method3 (Const S: String);

VAR

P: pinteger;

Begin

P: = pinteger (s);

P: = Pinteger (Integer (P) - 8);

Form1.Memo1.Lines.Add ('s reference count:' INTOSTR (P ^));

P: = Pinteger (SGLOBAL);

P: = Pinteger (Integer (P) - 8); Form1.Memo1.Lines.Add ('SGLOBAL reference count:' INTSTR (P ^));

Form1.Memo1.Lines.Add ('s address:' INTOSTR (Integer (Pointer (S))))

Form1.Memo1.Lines.Add ('');

END;

PROCEDURE SGLOBALINFO;

VAR

P: pinteger;

Begin

P: = Pinteger (SGLOBAL);

P: = Pinteger (Integer (P) - 8);

Form1.Memo1.Lines.Add ('sglobal reference count:' INTOSTR (P ^));

Form1.Memo1.Lines.Add ('sglobal address:' INTOSTR (Integer (Integer (SGLOBAL))

Form1.Memo1.Lines.Add ('');

END;

After the primary program is used in the main program, it is used to use these processes for the start-up SGLOBAL. We will see that the address of the three ways is the same as SGLOBAL. This preliminarily describes the VAR mode and the const mode is indeed transmitted by address. parameter. However, it is incredible that the default parameter transfer method will not generate a local copy for variables? Why is the address of the SGLOBAL? Because I didn't add a code for the code count, I didn't add a code for the quoted count, so I was very confused. Afterwards, Borland used the reference count and Copy-On-Write technology (for string, etc.), the data type of the data type of the two technologies, actually simply assigned a value to b, actually only assigning a value A address. B and add a reference count until one of the two is used to apply for a new memory space and copy A, and reduce A reference counts to optimize the operation of the string. Thus the D6DG and observes the assembly code and memory of Delphi (in the CPU window), the beginning of the conclusion of the string reference count is obtained. In this way, we can observe after the code is displayed, we can observe that the reference count of S and SGLOBAL when using the default mode, and the reference count count of both when other means is 1, which is more powerful. The Const mode is indeed passed by address, not like the default mode, just increasing the reference count. In this way, when we run the comment in the first row code in the first process, then run the program again, you can see that the address of S is different from SGLOBAL when you see the default mode, and the reference count counts are 1, indicating that it is true. It is a copy-on-write after S is modified. Then, now we know that the parameter type is a string, the parameter pass of the const mode is actually transmitting parameter addresses, which optimizes memory usage, and is the case when the parameter is other data type? To this end, the program just now is as follows, where IGLOBAL is a global plastic variable. Procedure method1 (i: integer); begin form1.memo1.Lines.Add ('i address:' INTOSTR (Integer))); Form1.Memo1.Lines.Add (''); end; procedure method2 ( Var i: integer; begin form1.memo1.lines.add ('i address:' INTOSTR (Integer (@i))); Form1.Memo1.Lines.Add (''); end; procedure method3 (Const i : Integer; begin form1.memo1.Lines.add ('i address:' INTOSTR (Integer)); Form1.Memo1.Lines.Add (''); end; procedure iglobalinfo; begin form1.Memo1 .LINES.ADD ('Iglobal Address:' INTOSTR (Integer (@iglobal))); Form1.Memo1.Lines.Add (''); end; in the main program, the initialized Iglobal is in real paragraph After the process, you can see that only the address of i in the VAR mode is the same as IGLOBAL, and the default mode and const will generate a local copy for Iglobal, and it is true that the Const will (also only) the parameters of the string and record types, such as D6DG. The memory is occupied during transmission.

转载请注明原文地址:https://www.9cbs.com/read-122681.html

New Post(0)