`
mmdev
  • 浏览: 13470247 次
  • 性别: Icon_minigender_1
  • 来自: 大连
文章分类
社区版块
存档分类
最新评论

delphi中指针的用法

 
阅读更多

delphi中指针的用法
[Delphi学习]浅谈Object Pascal的指针→ Kendy 发表于 2005-2-19 14:14:00
来源:HackDIY's Blog
大家都认为,C语言之所以强大,以及其自由性,很大部分体现在其灵活的指针运用上。因此,说指针是C语言的灵魂,一点都不为过。同时,这种说法也让很多人 产生误解,似乎只有C语言的指针才能算指针。Basic不支持指针,在此不论。其实,Pascal语言本身也是支持指针的。从最初的Pascal发展至今 的Object Pascal,可以说在指针运用上,丝毫不会逊色于C语言的指针。
以下内容分为八个部分,分别是
一、类型指针的定义
二、无类型指针的定义
三、指针的解除引用
四、取地址(指针赋值)
五、指针运算
六、动态内存分配
七、字符数组的运算
八、函数指针
一、类型指针的定义。对于指向特定类型的指针,在C中是这样定义的:
int *ptr;
char *ptr;
与之等价的Object Pascal是如何定义的呢?
var
ptr : ^Integer;
ptr : ^char;
其实也就是符号的差别而已。
二、无类型指针的定义。C中有void *类型,也就是可以指向任何类型数据的指针。Object Pascal为其定义了一个专门的类型:Pointer。于是,
ptr : Pointer;
就与C中的
void *ptr;
等价了。
三、指针的解除引用。要解除指针引用(即取出指针所指区域的值),C 的语法是 (*ptr),Object Pascal则是 ptr^。
四、取地址(指针赋值)。取某对象的地址并将其赋值给指针变量,C 的语法是
ptr = &Object;
Object Pascal 则是
ptr := @Object;
也只是符号的差别而已。
五、指针运算。在C中,可以对指针进行移动的运算,如:
char a[20];
char *ptr=a;
ptr++;
ptr+=2;
当执行ptr++;时,编译器会产生让ptr前进sizeof(char)步长的代码,之后,ptr将指向a[1]。ptr+=2;这句使得ptr前进两 个sizeof(char)大小的步长。同样,我们来看一下Object Pascal中如何实现:
var
a : array [1..20] of Char;
ptr : PChar; //PChar 可以看作 ^Char
begin
ptr := @a;
Inc(ptr); // 这句等价于 C 的 ptr++;
Inc(ptr, 2); //这句等价于 C 的 ptr+=2;
end;
六、动态内存分配。C中,使用malloc()库函数分配内存,free()函数释放内存。如这样的代码:
int *ptr, *ptr2;
int i;
ptr = (int*) malloc(sizeof(int) * 20);
ptr2 = ptr;
for (i=0; i<20; i++){
*ptr = i;ptr++;}
free(ptr2);
Object Pascal中,动态分配内存的函数是GetMem(),与之对应的释放函数为FreeMem()(传统Pascal中获取内存的函数是New()和 Dispose(),但New()只能获得对象的单个实体的内存大小,无法取得连续的存放多个对象的内存块)。因此,与上面那段C的代码等价的 Object Pascal的代码为:
var ptr, ptr2 : ^integer;
i : integer;
begin
GetMem(ptr, sizeof(integer) * 20);
//这句等价于C的 ptr = (int*) malloc(sizeof(int) * 20);
ptr2 := ptr; //保留原始指针位置
for i := 0 to 19 do
begin
ptr^ := i;
Inc(ptr);
end;
FreeMem(ptr2);
end;
对于以上这个例子(无论是C版本的,还是Object Pascal版本的),都要注意一个问题,就是分配内存的单位是字节(BYTE),因此在使用GetMem时,其第二个参数如果想当然的写成 20,那么就会出问题了(内存访问越界)。因为GetMem(ptr, 20);实际只分配了20个字节的内存空间,而一个整形的大小是四个字节,那么访问第五个之后的所有元素都是非法的了(对于malloc()的参数同 样)。
七、字符数组的运算。C语言中,是没有字符串类型的,因此,字符串都是用字符数组来实现,于是也有一套str打头的库函数以进行字符数组的运算,如以下代码:
char str[15];
char *pstr;
strcpy(str, "teststr");
strcat(str, "_testok");
pstr = (char*) malloc(sizeof(char) * 15);
strcpy(pstr, str);
printf(pstr);
free(pstr);
而在Object Pascal中,有了String类型,因此可以很方便的对字符串进行各种运算。但是,有时我们的Pascal代码需要与C的代码交互(比如:用 Object Pascal的代码调用C写的DLL或者用Object Pascal写的DLL准备允许用C写客户端的代码)的话,就不能使用String类型了,而必须使用两种语言通用的字符数组。其实,Object Pascal提供了完全相似C的一整套字符数组的运算函数,以上那段代码的Object Pascal版本是这样的:
var str : array [1..15] of char;
pstr : PChar; //Pchar 也就是 ^Char
begin
StrCopy(@str, 'teststr'); //在C中,数组的名称可以直接作为数组首地址指针来用
//但Pascal不是这样的,因此 str前要加上取地址的运算符
StrCat(@str, '_testok');
GetMem(pstr, sizeof(char) * 15);
StrCopy(pstr, @str);
Write(pstr);
FreeMem(pstr);
end;
八、函数指针。在动态调用DLL中的函数时,就会用到函数指针。假设用C写的一段代码如下:
typedef int (*PVFN)(int); //定义函数指针类型
int main()
{ HMODULE hModule = LoadLibrary("test.dll");
PVFN pvfn = NULL;
pvfn = (PVFN) GetProcAddress(hModule, "Function1");
pvfn(2);
FreeLibrary(hModule);}
就我个人感觉来说,C语言中定义函数指针类型的typedef代码的语法有些晦涩,而同样的代码在Object Pascal中却非常易懂:
type PVFN = Function (para : Integer) : Integer;
var
fn : PVFN;
//也可以直接在此处定义,如:fn : function (para:Integer):Integer;
hm : HMODULE;
begin
hm := LoadLibrary('test.dll');
fn := GetProcAddress(hm, 'Function1');
fn(2);
FreeLibrary(hm);
end;
分享到:
评论

相关推荐

    Delphi 7.0 After提取字符串中指定子字符串后的字符串.rar

    Delphi 7.0 提取字符串中指定子字符串后的字符串,这个平时在字符处理时候使用几率也挺高的,获取指定字符串后面的字符串,比如获取扩展名等也可以用此方法,本例中要用到After函数,测试时,当单击按钮时,执行以下...

    delphi考试题,(delphi)面试题

    Delphi 语言中,构造器(Constructor)和析构器(Destructor)是类中用于初始化和清理对象资源的方法。 - **构造器(Constructor)**:用于初始化对象,在创建对象时调用。 - **析构器(Destructor)**:用于清理...

    Delphi强悍的极简中间件(服务端和客户端)_源码.pdf

    最后,文档提供了详细使用说明书,以帮助开发者理解中间件的使用方法,并提供参考代码以供开发者学习和改进。 通过这个Delphi强悍的极简中间件,开发者可以以极简的代码实现强大的服务端和跨平台客户端,提供丰富的...

    Mscomm组件安装Delphi2010

    ### Mscomm组件在Delphi2010中的安装与配置 #### 一、Mscomm组件简介 Mscomm组件是Microsoft提供的用于实现串行通信的一种工具,它可以被多种编程语言所支持,包括Delphi。通过使用Mscomm组件,开发人员能够轻松地...

    delphi动态连接数据库

    本篇文章将深入探讨如何使用Delphi来动态连接SQL Server和Access数据库。 首先,Delphi提供了多种数据库访问组件,如DBXpress、ADO(ActiveX Data Objects)和DBExpress等,它们都支持动态数据库连接。对于SQL ...

    delphi ADO综合实例

    **Delphi ADO综合实例详解** 在Delphi编程环境中,ADO(ActiveX Data Objects)是...这个"Delphi ADO综合实例"就是一个很好的学习起点,涵盖了ADO组件的基本用法和常见操作,对于初学者和进阶开发者都极具价值。

    Delphi多线程Demo

    在`Execute`方法中,线程执行它的任务,并使用`PostMessage`将消息发送回主线程。主线程通过处理`WM_USER`消息来响应线程的通信。 通过这样的设计,开发者可以在多个线程之间安全地传递数据,同时保持各线程的独立...

    MDIform.rar_child delphi_delphi mdiform_子窗口

    MDIform 在 Delphi 中指的是一个支持MDI的应用程序主窗口,它能够承载多个子窗口(子窗体)。在这个"MDIform.rar"压缩包中,我们关注的是如何在Delphi中创建和管理这些子窗口,以及防止它们的重复打开,并检查子窗口...

    DELPHI基础知识

    "Object"在Delphi中指的是对象,它是面向对象编程的基础。Delphi使用Pascal语法定义类(class),并通过实例化类来创建对象。对象包含了数据(属性)和操作这些数据的方法。学习对象概念,包括继承、封装和多态性,...

    SXCopyHook_delphi7_sickcix_

    如果要深入理解这个程序的工作原理或使用方法,我们需要查看这个文本文件的内容。通常,这样的文件可能会有作者的注释,解释代码的功能和如何使用这些钩子功能。 总结来说,"SXCopyHook_delphi7_sickcix_"是一个用...

    Paint_form.rar_delphi form_delphi paint form_paint

    在Delphi中,通过理解和掌握Form的OnPaint事件、Canvas对象以及相关的绘图方法,开发者可以创建出丰富的自定义用户界面。无论是简单的图形还是复杂的动态效果,都可以通过熟练运用这些工具来实现。对于“Paint form ...

    delphi初学记录

    ### Delphi 初学者知识点汇总 #### 数据库操作技巧 1. **时间格式一致性** ...这些知识点覆盖了 Delphi 开发中数据库操作的一些基础技巧以及常用组件的使用方法,希望能够帮助初学者更好地掌握 Delphi 编程技能。

    Delphi高手突破-附录

    本文将详细介绍Object Pascal中指针的相关概念和用法。 #### 二、类型指针的定义 在C语言中,定义指向特定类型的指针非常直观,例如 `int *ptr;` 表示`ptr`是指向整型变量的指针。而在Object Pascal中,定义类似的...

    delphi 开发经验技巧宝典源码

    0034 在Delphi中禁止使用result 24 0035 如何在Delphi中录制代码 24 0036 如何编译器会提示数组太大时的处理技巧 25 0037 如何对超大数字进行计算 25 0038 强类型的定义及使用 25 2.2 类、函数、重载 25...

    delphi 开发经验技巧宝典源码06

    0034 在Delphi中禁止使用result 24 0035 如何在Delphi中录制代码 24 0036 如何编译器会提示数组太大时的处理技巧 25 0037 如何对超大数字进行计算 25 0038 强类型的定义及使用 25 2.2 类、函数、重载 25...

    截屏工具

    【控件】在Delphi中指的是用户界面(UI)元素,如按钮、文本框、菜单等,它们是构建用户交互界面的基础。在截屏工具的开发中,控件可能用于触发截图操作、显示预览、设置选项以及进行图像编辑等。Delphi的VCL库提供...

    XE2调用BPL和DLL方法

    3. 调用DLL方法:在主应用程序中,使用GetProcAddress函数获取DLL中的函数指针,然后通过这个指针调用DLL中的方法。注意,调用DLL方法时需确保遵循正确的调用约定。 在XE2中调用BPL或DLL中的FORM方法,可能涉及到...

    cxGrid指定列回车跳转

    5. **切换焦点**:利用cxGrid的`EditColumn`或`FocusedColumn`属性设置新的焦点列,并使用`Edit`方法开始编辑新列。 6. **阻止默认行为**:为了让回车键不执行其默认的结束编辑行为,需要调用`DefaultHandler`方法的...

    跟我一起写 Makefile

    什么是 makefile?...makefile 中指令的命令工具,一般来说,大多数的 IDE 都有这个命令,比如:Delphi 的 make,Visual C++的 nmake,Linux 下 GNU 的 make。可见,makefile 都成为了一种 在工程方面的编译方法。

Global site tag (gtag.js) - Google Analytics