在 Delphi 中创建一个包含外部 DLL 函数的类

3
我需要创建一个像这样的类
unit Classname;
interface
type

     TSomeClass = class
     public
       member1  : SomeType;
       member2  : AnotherDataType;


       ....
       function SomeFunction: SomeType; stadcall;external 'ExternalDll.dll';

 end;

能做到吗?

如何在Delphi中从类中声明一个外部函数(存储在C DLL中)

我正在使用Delphi 7。

提前致谢。


为什么你想让外部例程成为类的成员?通常它们是全局的。看一下Windows.pas并检查MessageBox等如何被导入。 - Uli Gerhardt
我非常确定这根本不可能。对于这种行为,您需要为每个类的实例加载一个单独的库实例,但这本身是不可能的,因为在同一进程中对同一DLL调用LoadLibrary超过一次会重复使用相同的实例。 - Jerry Dodge
感谢您的回答。 - J.C. Arteaga
@jerry 内部方法不会对每个对象实例都有一个代码实例。 - David Heffernan
@DavidHeffernan 对的,但那不是我想说的。我指的不是方法的实例,而是整个类的实例。 - Jerry Dodge
@jerry 这就是我所指的。实例方法(代码)将实例(数据)作为参数传递。 - David Heffernan
2个回答

3

外部函数不能是类声明的一部分。你需要用全局作用域声明外部函数,并安排类的方法调用该外部函数。


感谢您的回答。 - J.C. Arteaga

2
您可以创建一个带有伪方法的类,例如:
type
  TMyDllClass = class
  public
    NameOfDllEntryPoint: TFunctionTypeOfDllEntryPoint;
    constructor Create;
  end;

constructor TMyDllClass.Create;
begin
  inherited Create;
  LibHandle := LoadLibrary('path\to.dll');
  @NameOfDllEntryPoint := GetProcAddress(LibHandle, 'NameOfDllEntryPoint');
end;

MyDllClass := TMyDllClass.Create;
MyDllClass.NameOfDllEntryPoint(some, parameters);

这种方法很有效,我已经多次使用过,例如用于mitab.dll、libjpeg_turbo.dll和其他dll。其想法是减少全局函数对命名空间的干扰。

注意:为了清晰起见,我省略了任何错误处理(例如如果无法加载DLL或没有入口点)。在本例中,这将导致访问冲突,因为NameOfDllEntryPoint字段未被初始化。


就我个人而言,我从来不会直接将字段放在类的“public”部分。它们应该只存在于“private”部分,然后由实际函数包装,进而调用函数指针。这确保了这样的类成员保持只读状态。 - Jerry Dodge
1
它甚至无法编译 - 字段必须在方法之前。 - Jerry Dodge
@JerryDodge:如果你把它们放在一个新的公共块中,它就可以工作。 - Rudy Velthuis
@Rudy 对,但这个答案并不是这样写的。只是指出一下。 - Jerry Dodge
@JerryDodge 我没有尝试编译那段代码。我认为这不是必要的,但现在已经改变了顺序。关于公共部分没有字段的问题:将该字段移动到私有部分,并创建一个公共只读属性来访问它。问题解决了。 - dummzeuch

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接