程序员指针简介

不管你意识到与否,你所使用的绝大多数程序都以某种方式使用指针。作为一名程序员,您需要了解指针是如何工作的。...

不管你意识到与否,你所使用的绝大多数程序都以某种方式使用指针。也许您在某个时候遇到过NullPointerException。作为程序员,您编写的代码很可能会使用指针,即使您自己没有实现它们。

intro-pointers-programming

今天我将向您展示指针是如何工作的,因此您可能希望在编程入门中了解数组和列表是如何工作的。这篇文章将比通常更以理论为基础,但坚持下去,指针是非常复杂的!

编译代码

在深入研究指针之前,您需要了解代码是如何构建和执行的——也许您已经知道这一点了。本节将有相当一般性的陈述——适用于大多数语言,但不一定适用于所有语言。

Pointers

让我们回到起点。每台计算机都使用二进制,一系列的1和0组成了我们所知道的现代技术。用二进制代码编写任何东西都是非常困难的(文件会非常混乱),因为这些是中央处理器或CPU运行所需的原始指令。这就是机器代码。

机器代码的下一步是组装。这是一种人类可读的格式。虽然编程仍然很复杂,但这是可能的。汇编是由一系列执行任务的简单命令组成的,被称为低级编程语言。编写复杂的程序是可能的,但是很难表达抽象的概念,而且需要大量的考虑。

许多视频游戏和高性能应用程序都有汇编语言编写的一些逻辑,因为如果您知道自己在做什么,就可以发现一些真正的速度提升。但是,对于绝大多数编程项目,您根本不需要知道任何程序集。

Pointers

所以,如果机器代码太难写,汇编程序太难编程,你用什么来写代码呢?这就是高级语言的用武之地。高级语言使程序易于编写。你可以用与你的母语相似的语言编程,而且很容易表达复杂的算法。您可能听说过许多高级语言(您肯定会使用这些语言编写的程序):

  • 基本
  • C++
  • 口齿不清

这些语言现在已经很古老了,很多都是在20世纪50年代早期发展起来的!几乎所有现代编程语言都是高级语言,包括PHP和Python。每天都有更多的语言被发明出来(虽然现在可能已经足够了),但是如果计算机需要机器代码,那么你的代码到底是如何正常工作的呢?

这就是编译的用武之地。编译器是将高级代码转换为可执行形式的程序。这可能是另一种高级语言,但通常是汇编语言。一些语言(如Python或Java)将代码转换为一个称为字节码的中间阶段。这将需要在以后再次编译,这通常是在需要时完成的,比如在程序运行时。这就是所谓的即时编译,它非常流行。

内存管理

既然您知道了编程语言是如何工作的,那么让我们看看高级语言中的内存管理。对于这些示例,我将使用伪代码——不是用任何特定语言编写的代码,而是用来显示概念而不是确切的语法。今天,这将最类似于C++,因为这是最好的高级语言(在我看来)。

在本节中,如果您了解RAM的工作原理,将会有所帮助。

大多数语言都有变量——存储一些数据的容器。必须显式定义数据类型。一些动态类型语言(如Python或PHP)可以为您处理这个问题,但它们仍然必须这样做。

假设您有一个变量:

int myNumber;

这段代码声明了一个名为myNumber的变量,并给它一个integer的数据类型。编译后,计算机将此命令解释为:

查找一些空内存,并保留足够大的空间来存储整数

一旦这个命令被执行,那个内存位就不能被另一个程序使用。它还不包含任何数据,但它是为myNumber变量保留的。

现在为变量赋值:

myNumber = 10;

要完成此任务,您的计算机将访问其保留的内存位置,并将其中存储的任何值更改为新值。

现在,这一切都很好,但内存位置如何得到保留?如果程序保留了它们喜欢的所有内存,RAM会立即填满——这将导致系统速度非常慢。

Pointers

为了避免这个潜在的问题,许多语言实现了一个垃圾收集器,用于销毁超出范围的变量(从而释放保留的内存位置)。

你可能想知道什么是范围,为什么它如此重要。作用域定义了程序使用的变量或任何内存的限制和寿命。当任何代码都无法访问某个变量时(即垃圾收集器介入时),该变量就“超出范围”。举个例子:

function maths() { int firstNumber = 1;}int secondNumber = 2;print(firstNumber + secondNumber); // will not work

这个例子不会编译。变量firstNumber在数学函数中,所以这就是它的作用域。不能从声明它的函数外部访问它。这是一个重要的编程概念,理解它对于使用指针至关重要。

这种处理内存的方法称为堆栈。这是绝大多数程序的工作方式。使用它不需要理解指针,而且它的结构相当好。堆栈的缺点是速度。由于计算机必须分配内存、跟踪变量并运行垃圾回收,因此开销很小。这对于较小的程序来说很好,但是对于高性能任务或数据密集型应用程序呢?

输入:指针。

指针

表面上看,指针听起来很简单。它们引用(指向)内存中的一个位置。对于堆栈上的“常规”变量来说,这似乎没有什么不同,但是相信我,这是一个巨大的差异。指针存储在堆上。这与堆栈相反—它的组织性较差,但速度要快得多。

让我们看看如何在堆栈上分配变量:

int numberOne = 1;int numberTwo = numberOne;

这是简单的语法;变量numberTwo包含数字1。赋值过程中,它的值从numberOne变量复制过来。

如果要获取变量的内存地址,而不是它的值,则必须使用与号(&)。这称为操作符的地址,是指针工具箱的重要部分。

int numberOne = 1;int numberTwo = &numberOne;

现在numberTwo变量指向一个内存位置,而不是将数字1复制到它自己的新内存位置。如果要输出这个变量,它将不是第一个变量(即使它存储在内存位置)。它将输出它的内存位置(可能类似于2167,尽管它根据系统和可用的RAM而变化)。要访问存储在指针中的值,而不是内存位置,必须取消对指针的引用。这将直接访问该值,在本例中,该值将是第一个值。以下是取消引用指针的方法:

int numberTwo = *numberOne;

解引用运算符是星号(*)。

这可能是一个很难理解的概念,所以让我们再看一遍:

  • 运算符(&)的地址存储内存地址。
  • 解引用运算符(*)访问该值。

声明指针时语法略有变化:

int * myPointer;

int的数据类型在这里指的是指针指向的数据类型,而不是指针本身的类型。

现在你知道指针是什么了,你可以用它们做一些非常巧妙的把戏了!使用内存时,操作系统会按顺序启动。你可以把公羊看作鸽子洞。很多洞用来存放东西,一次只能用一个。不同的是,这些鸽子洞都有编号。分配内存时,您的操作系统从最低的数字开始,然后开始工作。它永远不会在随机数之间跳来跳去。

Pointers

在使用指针时,如果已经分配了数组,则可以通过简单地递增指针来轻松导航到下一个元素。

这就是有趣的地方。将值传递给函数(使用存储在堆栈上的变量)时,这些值会被复制到函数中。如果这些是大变量,那么程序现在将存储它们两次。函数完成后,可能需要一种方法来返回这些值。函数通常只能返回一件事——所以如果要返回两件、三件或四件事呢?

Pointers

如果将指针传递给函数,则只复制内存地址(非常小)。这节省了你的CPU很多工作!也许你的指针指向一个巨大的图像数组——你的函数不仅可以处理存储在完全相同的内存位置的完全相同的数据,而且一旦完成,就不需要返回任何东西。干净利落!

不过,你必须非常小心。指针仍然可以超出范围并由垃圾收集器收集。但是,存储在内存中的值不会被收集。这称为内存泄漏。您不能再访问数据(因为指针已被销毁),但它仍在使用内存。这是许多程序崩溃的一个常见原因,如果有大量数据,它可能会严重失败。大多数情况下,如果你有一个大的漏洞(使用比系统更多的RAM),你的操作系统会杀死你的程序,但这是不可取的。

Pointers

调试指针可能是一场噩梦,尤其是在处理大量数据或在循环中工作时。它们的缺点和难以理解的地方确实值得您在性能方面进行权衡。尽管记住,它们可能并不总是必需的。

今天到此为止。我希望你在一个复杂的话题上学到了一些有用的东西。当然,我们还没有涵盖所有需要知道的事情——这是一个非常复杂的话题。如果你对学习有兴趣,我强烈推荐在24小时内使用C++。

如果这有点复杂,请看一下我们的最简单编程语言指南。

你今天学过指针是怎么工作的吗?你有什么技巧和窍门想和其他程序员分享吗?跳到下面的评论和分享你的想法!

  • 发表于 2021-03-15 04:42
  • 阅读 ( 180 )
  • 分类:编程

你可能感兴趣的文章

分配(calloc)和马洛克(malloc)的区别

...储相同类型元素的固定大小的顺序集合。它是一个数组。程序员必须声明数组大小。如果程序员声明五个元素的整数数组,则不可能为大于声明大小的索引赋值。内存分配是固定的,不能在运行时更改。另一种内存分配方法是动...

  • 发布于 2020-10-24 03:58
  • 阅读 ( 150 )

指针(pointer)和参考(reference)的区别

指针(pointer)和参考(reference)的区别 在讨论指针和引用之间的区别之前,让我们先简单地看一下这两个术语的含义。在程序中,数据占用内存。为了访问数据,应该知道数据在执行时被放在内存中的确切位置。指针变量和引用...

  • 发布于 2020-10-28 19:41
  • 阅读 ( 260 )

如何快速调整mac上dock的大小

...下面是如何在macOS中快速调整Dock的大小。 如何使用鼠标指针快速调整dock的大小 首先,这里有一个快速简单的方法来调整你的码头。查看桌面时,将鼠标指针悬停在Dock中的垂直分隔线上,该分隔线位于应用程序图标区域和文件...

  • 发布于 2021-04-01 10:14
  • 阅读 ( 141 )

如何在ipad上使用和自定义光标

...设置”应用程序中,转到“辅助功能”部分,然后选择“指针控制”选项。 在这里,在“外观”部分,您可以点击“增加对比度”旁边的切换,使指针更容易看到。 您也可以点击“自动隐藏指针”选项来更改指针消失前的空...

  • 发布于 2021-04-02 11:20
  • 阅读 ( 219 )

如何在Windows10上更改鼠标指针的颜色和大小

...光标主题始终是可能的,但是现在您可以不用安装自定义指针主题就可以这样做了。 要找到此选项,请转至“设置”>“易访问性”>“光标和指针”。(您可以按Windows+I快速打开设置应用程序。) 要更改指针的大小,请拖...

  • 发布于 2021-04-03 09:33
  • 阅读 ( 261 )

如何在windows中调整鼠标设置

...者在拖动时按住鼠标按钮有困难,则此功能非常有用。 指针 “指针”选项卡允许您更改鼠标指针的外观以及伴随鼠标指针的上下文光标。“Scheme”下拉列表中的指针和光标的各种集合是大多数人想要的:您可以切换到黑色或白...

  • 发布于 2021-04-07 06:12
  • 阅读 ( 251 )

如何在windows中自动启用或禁用“增强指针精度”

Windows的“增强指针精度”设置对某些鼠标有帮助,但对其他鼠标有伤害。如果您发现它一直自动启用或禁用自己,这里有一些潜在的修复方法。 相关:如何在Windows中提高鼠标指向的准确性 这个选项很有趣,你可以在控制面板&...

  • 发布于 2021-04-08 13:02
  • 阅读 ( 158 )

使鼠标指针远离正在键入的内容

如果你的鼠标指针似乎总是在你打字的时候挡住了你的去路,你并不是一个人…你点击一些文本的中间并开始输入更多的内容,但是光标仍然挡住了你的去路。有一个叫做MouseAway的小实用程序可以帮你解决这个问题…它不是新的...

  • 发布于 2021-04-14 11:45
  • 阅读 ( 98 )

如何在mac上使用可见的鼠标光标拍摄屏幕截图

当在Mac上截图时,Mac屏幕截图工具通常隐藏鼠标指针,这样它就不会妨碍它的前进。但是有时候,您需要捕获指针来正确地说明一些事情。幸运的是,使用简单的选项很容易打开。下面是方法。 要在屏幕截图中捕获鼠标光标,...

  • 发布于 2021-04-14 16:33
  • 阅读 ( 203 )

smart dot将您的智能手机变成时尚的鼠标和激光指针

当然,激光指针通常要花一美元左右,但有多少能连接到自己的应用程序呢?韩国Tangram公司生产的智能点是一种微小的拉丝金属配件,可以安装在智能**的耳机插孔中。一旦连接起来,它可以像一个简单的激光指针或鼠标一样工...

  • 发布于 2021-04-21 22:14
  • 阅读 ( 134 )
zsb73023
zsb73023

0 篇文章

相关推荐