2009-10-22 5 views
11

A menudo hago pequeños métodos para ayudar a la depuración, que no se utilizan en el programa real. Normalmente, la mayoría de mis clases tienen un método AsString que agrego a los relojes. Sé Delphi 2010 tiene visualizadores, pero todavía estoy en 2007.¿Cómo forzo al enlazador a incluir una función que necesito durante la depuración?

Considere este ejemplo:

program Project1; 

{$APPTYPE CONSOLE} 

uses SysUtils; 

type 
    TMyClass = class 
    F : integer; 
    function AsString : string; 
    end; 

function TMyClass.AsString: string; 
begin 
    Result := 'Test: '+IntToStr(F); 
end; 

function SomeTest(aMC : TMyClass) : boolean; 
begin 
    //I want to be able to watch aMC.AsString while debugging this complex routine! 
    Result := aMC.F > 100; 
end; 

var 
    X : TMyClass; 

begin 
    X := TMyClass.Create; 
    try 
    X.F := 100; 
    if SomeTest(X) 
     then writeln('OK') 
     else writeln('Fail'); 
    finally 
    X.Free; 
    end; 
    readln; 
end. 

Si añado X.AsString como un reloj, apenas consigo "la función que se llamará, TMyClass .AsString, fue eliminado por el enlazador ".

¿Cómo fuerzo al enlazador para que lo incluya? Mi truco habitual es utilizar el método en algún lugar del programa, pero ¿no hay una forma más elegante de hacerlo?

RESPUESTA: GJ proporcionó la mejor manera de hacerlo.

initialization 
    exit; 
    TMyClass(nil).AsString; 

end. 

Respuesta

6

sveinbringsli preguntar: "¿Tiene un consejo para las funciones de la unidad también?"

Delphi compilador es inteligente ... para que pueda hacer algo como ...

unit UnitA; 

interface 

{$DEFINE DEBUG} 

function AsString: string; 

implementation 

function AsString: string; 
begin 
    Result := 'Test: '; 
end; 

{$IFDEF DEBUG} 
initialization 
    exit; 
    AsString; 
{$ENDIF} 
end. 
+0

+1. Eso es lo que suelo hacer. Colóquelo en un bloque de inicialización para que no se vincule. –

+0

Estaba batallando conmigo mismo sobre qué respuesta debería aceptar, esta o la otra respuesta con el "truco publicado". Elegí esta porque no afectará la versión de lanzamiento. –

+0

Sí, y si su función necesita algunos parámetros como variables, solo escriba en la sección de inicialización: "si @AsString = nil then;" en lugar de poner parámetros en. –

6

Puede hacer que la función se publique.

TMyClass = class 
    F : integer; 
    published 
    function AsString : string; 
    end; 

y el interruptor de encendido en 'Propiedades del reloj' 'Permitir llamadas de función'

+0

Gran! No sabía que los métodos publicados funcionaron de esa manera. ¿Tiene un consejo para las funciones de la unidad también? –

+0

También puede poner "publicado" como: {$ IFDEF DEBUG} publicado {$ ENDIF} –

0

Tal vez funcione a llamarlos de alguna sección de inicialización, custodiadas por {DEBUG IFDEF} o {IFOPT D +}.

+0

Sí, esto funcionaría, pero quiero encontrar una manera que _no requiera que realmente llame a la función en alguna parte. –

+0

Por supuesto que sería bueno tenerlo. Pero al menos es una solución que no carga la versión de lanzamiento. (Qué truco publicado de GJ sería, BTW. :-)) –

Cuestiones relacionadas