数组类型与数组指针的巧妙利用

本例通过存取结构, 慢慢引入了数组类型与指针的一些使用方法; 其中六个小例子的测试内容和结果都是一样的.


unit Unit1;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls;

type
  TForm1 = class(TForm)
    Button1: TButton;
    Button2: TButton;
    Button3: TButton;
    Button4: TButton;
    Button5: TButton;
    Button6: TButton;
    procedure Button1Click(Sender: TObject);
    procedure Button2Click(Sender: TObject);
    procedure Button3Click(Sender: TObject);
    procedure Button4Click(Sender: TObject);
    procedure Button5Click(Sender: TObject);
    procedure Button6Click(Sender: TObject);
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

type {先定义结构和结构指针}
  PMyRec = ^TMyRec;
  TMyRec = record
    F1: Char;
    F2: Word;
  end;

{用静态数组储存或读写结构很方便}
procedure TForm1.Button1Click(Sender: TObject);
var
  ArrRec: array[0..2] of TMyRec;
  i: Integer;
begin
  {写入}
  for i := 0 to 2 do
  begin
    ArrRec[i].F1 := Chr(i+65);
    ArrRec[i].F2 := (i+1) * 10;
  end;

  {读取}
  for i := 0 to Length(ArrRec) - 1 do
    ShowMessageFmt(‘%s, %d‘, [ArrRec[i].F1, ArrRec[i].F2]);
end;

{这个只是定义了一块内存, 没用数组的概念, 有点麻烦}
procedure TForm1.Button2Click(Sender: TObject);
var
  buf: PMyRec;
begin
  GetMem(buf, SizeOf(TMyRec) * 3); {申请内存}

  {写入}
  buf^.F1 := ‘A‘;
  buf^.F2  := 10;
  Inc(buf);       {到下一个}
  buf^.F1 := ‘B‘;
  buf^.F2  := 20;
  Inc(buf);
  buf^.F1 := ‘C‘;
  buf^.F2  := 30;

  Dec(buf, 2);    {回到开始}

  {读取}
  ShowMessageFmt(‘%s, %d‘, [buf^.F1, buf^.F2]);
  Inc(buf);       {到下一个}
  ShowMessageFmt(‘%s, %d‘, [buf^.F1, buf^.F2]);
  Inc(buf);
  ShowMessageFmt(‘%s, %d‘, [buf^.F1, buf^.F2]);

  Dec(buf, 2);    {回到开始}
  FreeMem(buf);   {释放内存}
end;

{可以给结构定义一个数组类型}
procedure TForm1.Button3Click(Sender: TObject);
type
  TArr = array of TMyRec;
var
  buf: PMyRec;
  i: Integer;
begin
  GetMem(buf, SizeOf(TMyRec) * 3);

  for i := 0 to 2 do
  begin
    TArr(buf)[i].F1 := Chr(i+65);
    TArr(buf)[i].F2 := (i+1) * 10;
  end;

  for i := 0 to 2 do
    ShowMessageFmt(‘%s, %d‘, [TArr(buf)[i].F1, TArr(buf)[i].F2]);

  FreeMem(buf);
end;

{直接用动态数组也行}
procedure TForm1.Button4Click(Sender: TObject);
var
  Arr: array of TMyRec;
  i: Integer;
begin
  SetLength(Arr, 3);
  for i := 0 to 2 do
  begin
    Arr[i].F1 := Chr(i+65);
    Arr[i].F2 := (i+1) * 10;
  end;

  for i := 0 to 2 do
    ShowMessageFmt(‘%s, %d‘, [Arr[i].F1, Arr[i].F2]);
end;

{使用一个元素的数组指针, 这是很常用的}
procedure TForm1.Button5Click(Sender: TObject);
type
  PArr = ^TArr;
  TArr = array[0..0] of TMyRec;
var
  buf: PArr;
  i: Integer;
begin
  GetMem(buf, SizeOf(TMyRec) * 3);

  for i := 0 to 2 do
  begin
    buf^[i].F1 := Chr(i+65);
    buf^[i].F2 := (i+1) * 10;
  end;

  {用这种方法不能像下面这样读写, 也就是 [] 中不能是超过 0 的常数, 但可以用变量}
  {这也容易理解, 因为常量会直接编译到代码中, 在没有分配内存以前, 编译器不知道数组会更大}
  {要解决这个问题需要用下一个方法}
//  buf[0].F1 := ‘A‘;
//  buf[0].F2 := 10;
//  buf[1].F1 := ‘B‘;
//  buf[1].F2 := 20;
//  buf[2].F1 := ‘C‘;
//  buf[2].F2 := 30;

  for i := 0 to 2 do
    ShowMessageFmt(‘%s, %d‘, [buf[i].F1, buf[i].F2]);

  FreeMem(buf);
end;

{使用一个超大的数组指针, Delphi 的 TList 类就是这么干的}
procedure TForm1.Button6Click(Sender: TObject);
type
  PArr = ^TArr;
  TArr = array[0..100000] of TMyRec; {不要担心内存暴涨, 使用时我们只用其指针}
var
  buf: PArr;
  i: Integer;
begin
  GetMem(buf, SizeOf(TMyRec) * 3);

  for i := 0 to 2 do
  begin
    buf^[i].F1 := Chr(i+65);
    buf^[i].F2 := (i+1) * 10;
  end;

  {和上例不同的是, 下面的代码也可以}
//  buf[0].F1 := ‘A‘;
//  buf[0].F2 := 10;
//  buf[1].F1 := ‘B‘;
//  buf[1].F2 := 20;
//  buf[2].F1 := ‘C‘;
//  buf[2].F2 := 30;

  for i := 0 to 2 do
    ShowMessageFmt(‘%s, %d‘, [buf[i].F1, buf[i].F2]);

  FreeMem(buf);
end;

end.

原文地址:https://www.cnblogs.com/h2zZhou/p/11435276.html

时间: 2024-10-26 07:14:11

数组类型与数组指针的巧妙利用的相关文章

C语言 数组类型与数组指针类型

//数组类型与数组指针类型 #include<stdio.h> #include<stdlib.h> #include<string.h> void main(){ printf("\n-------数组类型----------\n"); { //定义一个数组类型 typedef int Myarr[5];//定义了一个int型有5个元素的数组类型 //定义一个数组类型变量 Myarr myarr; //数组赋值 int i = 0; for (i

201506111312_《JavaScript权威指南——找元素位置函数、数组类型、数组对象》(p159-?)

1. indexOf();    lastIndexOf(); 例如: 2. 找元素位置函数findAll(); var arr = [6,4,6,33,576,0.145,36,66,814,'apple','person',12];function findAll(a,x) { var results = [], len = a.length, pos = 0; while(pos < len) { pos = a.indexOf(x,pos); if(pos === -1) break;

php中对象类型与数组之间的转换

1.刚看视频学习的时候看到一个困扰很久的问题, 有时候我们在进行做项目的时候会碰到的一个小问题.举一个小例子.  获取一个xml文件里面的数据. xml.xml文件如下: <?xml version="1.0" encoding="ISO-8859-1"?><note> <to>George</to> <from>John</from> <heading>Reminder</h

静态数组和动态数组

概念 数组在程序设计中应用十分广泛,可以用不同类型的数组来存储大量相同类型的数据.创建数组的方式一般有三种: 全局/静态范围的数组.局部变量数组.申请堆空间创建的数组.其中,全局/静态范围的数组以及局部变量数组都属于静态数组,从堆中申请空间建立的数组为动态数组. 静态数组和动态数组的区别 1.静态数组的大小是在编译期间就确定,并且分配的,其内存在使用结束后由计算机自动释放,效率高:动态数组是在程序运行时,由程序员根据实际需要从堆内存中动态申请的,使用结束后由程序员进行释放,效率低. 2.对静态数

数组Array、数组API

1.数组:批量管理多个数据的存储空间. 数组的作用:现实中,批量管理多个数据都是集中分组存放,良好的数据结构,可极大提高程序的执行效率! 优点:方便查找 2.创建数组:(4种方式) (1)var 变量名=[]; 创建一个空数组 何时使用:暂时不知道数组中的元素内容时(2)var 变量名=[值1,值2,...]; -->创建数组同时,初始化数组中的数据(3)var 变量名=new Array(); 创建一个空数组 new:在window之外,创建一个新空间,保存多个数据 返回新空间的地址! 注意:

一维数组,二维数组,三维数组,数组与指针,结构体数组,通过改变指针类型改变访问数组的方式

 打印数组中的每个元素,打印每个元素的地址: #include <stdio.h> #include <stdlib.h> void main(void) { int a[10] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 }; for (int *p = a; p < a + 10;p++)  //指针类型决定4个字节 { printf("\n%p,%d", p, *p); } getchar(); } 指针数组 #inclu

使用函数指针,完成一个sort()函数,能对任何类型的数组元素进行排序: 回调函数 以及 memcpy ()原型实现

进来复习了一下C语言指针,一直没有写过太多关于函数指针的代码,而且对回调函数的理解一直都是在理论上,基本上没有太写过关于它的代码,进来得空,写了一个小程序加深下自己对回调函数和函数指针的理解. 问题描述: 编写一个sort()函数,使它能够对任何类型的数组元素进行排序. 下面是我写的代码: /* 使用函数指针的回调函数技巧,设计一个能排序int 和char 数组的sort()函数 */ #include<stdio.h> #include<stdlib.h> #include<

#运算符、不同的指针类型、数组和指针、指针运算、堆、栈、静态区、只读区、下标VS指针

#运算符:用于在预编译期将宏参数转换为字符串 #define CONVERS(x)  #x   //注:没用双引号包括. 不同类型的指针占用的内存空间大小相同. 局部变量 定义: a[5]; 打印a[i]时,a[i]为随机数. 若定义a[5]={1,2}; 打印时,a[0]=1;a[1]=2;a[2]=a[3]=a[4]=0; 数组地址与数组名: 1.数组名代表数组首元素的地址.  a=&a[0]; 2.数组的地址需要用取地址符号&才能得到 (&a) 3.数组首元素的地址值与数组的

巧妙利用快速排序法的原理求一个数组中的第10大元素

//快速排序法 int QuickSort_process3(int *a, int low, int high) { int l, h, temp; l = low; h = high; temp = a[low]; while (l < h){ while (l< h&&a[h] >= temp) --h; if (l < h) a[l] = a[h]; while (l < h&&a[l] < temp) ++l; if (l &l