我们前面讲到的赋值语句是最简单的赋值语句。出现在赋值符号左边的只是一个简单的变量名。实际上,能够出现在赋值符号左边的内容远远不止如此。我们下面就来讲解更加复杂的赋值语句——复合结构的赋值。

复合结构的赋值

什么叫做复合结构呢?比如,我们大家一般都用过手机,也应该都知道,手机里面有个联系人名录,里面记录了联系人的姓名、手机、住宅电话、公司电话、备注等信息。在这个例子里面,每个联系人条目就是一个包含了姓名、手机、住宅电话、公司电话、备注等信息的复合结构。

这个概念不难理解,但是,如果认真详细解释起来,还需要费一大堆口舌。本书不打算在这种简单易懂的概念上浪费口水。读者如果有什么不明白的,可以参考具体语言中的复合结构的概念和定义。比如,在C语言中,复合结构的对应数据类型叫做“structure”(结构)。在C++、Java、Python、Ruby等更加高级的面向对象的语言当中,复合结构的对应数据类型叫做“Class”(类)。

面向对象是一个非常重要的概念,是命令式编程语言的主流编程模型,后面会加以详细讲述。

现在,假设我们有一个叫做contact(联系方式)的复合结构数据,其中包含name、mobile、home_phone、office_phone、memo等属性。我们就可以这样一条条设置contact这个数据的每一个属性。

contact.name = “Tom”

contact.mobile = “1338978776”

contact.home_phone = “8978776”

contact.office_phone = contact.home_phone

contact.memo = “Tom is a SOHO. He works at home.”

上述语句中的“.”表示访问复合结构的内部数据。比如,contact.name就表示contact这个复合结构数据中的name属性。这也是高级命令式语言的一种语法惯例。

从上面的例子中可以看到,复合结构变量的属性的用法和简单变量完全相同。复合结构变量的属性既可以出现在赋值符号的左边,也可以出现在赋值符号的右边。比如,contact.home_phone先是出现在“=”的左边,接着又出现在“=”的右边。

那么,我们如何在内存结构中理解复合结构呢?首先,我们还是要给内存单元贴上标签。我们想象一下,在一个布满了小格子的大柜子里面,选出一个小格子,然后在上面贴上“contact”这个标签。然后,我们从贴上“contact”的那个小格子开始,根据每个属性的数据宽度(即占用最小内存单元的个数),依次贴上“name”、“mobile”、“home_phone”、“office_home”、“memo”等几个标签。

在这个例子中,“contact”就相当于内存中的一个基本地址,而那些属性则相当于以基本地址为基础的几个偏移地址。

当我们访问contact的属性的时候,实际上就相当于访问“contact”基本地址再加上属性偏移地址的那个单元格的内容。比如,contact.name实际上就是contact基本地址加上name属性偏移地址之后的那个单元格的内容。对于复合结构的属性的访问,实际上就是一次内存中的间接寻址。

当我们定义了一个包含了多个属性的复合结构的时候,实际上就相当于我们自己定义了一套内存结构映射方案。这还不是最简单的情况,复合结构里面还有可能包含复合结构。事实上,复合结构的嵌套层次是没有限制的,可以嵌套到任意深度。因此,我们有可能写出这样的访问深层次属性的代码:contact.address.city.zipcode。

我们需要把复合结构的概念理解道内存结构映射的层次吗?需要。即使你现在不需要,以后早晚也会需要。随着你对编程语言掌握的深入,你早晚需要理解到这个层次。与其到时候费二遍功,还不如现在就一次搞定。

下面我们看看数组类型的复合结构在内存中的映射。

数组类型内存映射

复合结构并非唯一的内存结构映射定义。在命令式语言中,还有一个极为常见的类型——数组类型,同样对内存结构进行了映射。

数组类型对内存结构的映射是一种十分整齐的映射。我们可以想象一列整整齐齐的单元格,每个单元格的数据宽度完全相等。因此,我们可以通过简单的等距位移来访问其中某一个单元格的内容。事实上,数组正是通过数字下标来访问其中某一个位置的数据的。

比如,假设我们有一个数组变量array。我们可以想象一列长长的宽度相同的单元格,第一个单元格上贴着一个标签“array”。

我们想访问array数组中第30个数据。我们就可以这么写,array[30],就可以定位到array数组的第30个数据单元。

“[]”这样的方括号,表示访问一个数组中的某一个位置。这也是高级命令式语言的一种语法惯例。

同样,array[30]可以出现在赋值表达式的左边,也可以出现在赋值表达式的右边。比如:

array[30] = 1

array[31] = array[30]

需要注意的是,在很多命令式语言中,数组下标是从0开始的。因此,如果我们想访问第30个数据单元,很多情况下,我们必须写成array[29]。

综上所述,出现在赋值符号左边的变量,主要就是三种——简单变量、复合结构变量、数组变量。而且,这三种变量都有一个特点,他们都可以唯一定位到内存中的某一个具体位置。这体现了赋值语句的最根本的含义——将一个表达式执行的结果存入到某一个指定的内存单元中去。我们对赋值语句的理解,必须达到这个层次,才能够正确理解随之而来的一系列相关概念。

另外,在一些更高级别的命令式编程语言(如Python、Ruby等),实现了部分函数式编程语言(Functional Programming Language)的部分特性,如模式匹配(Pattern Match)这样的特性。在这些语言中,有可能出现一次对多个变量同时赋值的赋值语句。比如:

(a, b) = (1, 2)

a, b = 1, 2

某些情况下,这种语法用起来相当方便。比如,某个复合结构中有多个属性,我们想就把其中一些属性一次性复制到多个变量中的时候,就可以这么写。

想深入了解这种语法的读者,可以去研究一下函数式编程语言中的模式匹配特性。

当然,在我个人看来,即使在函数式编程语言中,模式匹配也不是什么核心的概念,只不过是一种简化书写的语法糖。掌握不掌握,都对编程核心概念的理解没有什么本质影响。

以上讲述的赋值语句都是“显式”赋值语句,即存在明确的赋值符号(=)的赋值语句。除了显式赋值语句之外,还有一种特殊的隐式赋值语句——参数传递。这个在后面小节再做介绍。

python复合赋值语句语法_复合结构的赋值语句理解相关推荐

  1. python格式化字符串语法_详解Python3 中的字符串格式化语法

    一.旧式的字符串格式化 % 操作符 参考以下示例: >>> name = "Eric" >>> "Hello, %s." % ...

  2. python点操作符语法_最基础的python语法

    最基础的pyth语法 1 python严格区分大小写 2 Python中的每一行就是一条语句,每条语句以换行结束 print(1233) print('eeeee') 3 多行编写时语句后边以\结尾 ...

  3. python有多少种语法_这20个常规Python语法你都搞明白了吗?

    Python简单易学,但又博大精深.许多人号称精通Python,却不会写Pythonic的代码,对很多常用包的使用也并不熟悉.学海无涯,我们先来了解一些Python中最基本的内容. Python的特点 ...

  4. python关闭对象语法_用Python打开和关闭文件

    到目前为止,您一直在读取和写入标准输入和输出.现在,我们将看到如何使用实际数据文件. Python提供了默认情况下处理文件所必需的基本功能和方法.您可以使用文件对象执行大多数文件操作. open函数 ...

  5. python十大语法_精华-Python十大语法有哪些?

    Python是某种象征简易观念的语言,其语法相比简易,特别容易入门.然而,假如此后小视Python语法的精妙和深邃,那便大错特错了.文中细致挑选了最能体现Python语法之精妙的十个知识要点,并另附完 ...

  6. python装饰器 稀里糊涂_谈谈自己的理解:python中闭包,闭包的实质

    闭包这个概念好难理解,身边朋友们好多都稀里糊涂的,稀里糊涂的林老冷希望写下这篇文章能够对稀里糊涂的伙伴们有一些帮助~ 请大家跟我理解一下,如果在一个函数的内部定义了另一个函数,外部的我们叫他外函数,内 ...

  7. python大牛 关东升_《Python从小白到大牛》第4章 Python语法基础

    本章主要为大家介绍Python的一些语法,其中包括标识符.关键字.常量.变量.表达式.语句.注释.模块和包等内容. 标识符和关键字 任何一种计算机语言都离不开标识符和关键字,因此下面将详细介绍Pyth ...

  8. python 循环赋值_计算机二级Python语言程序设计 第2章Python语言基本语法元素

    第二章学习知识导图 本章概述:本章目的是了解基础的Python相关知识 考点主要是: 1) 程序的基本语法元素:程序的格式框架.缩进.注释.变量.命名.保留字.数据类型.赋值语句.引用 2) 基本输入 ...

  9. 一张图了解python基本语法_一张图认识Python(附基本语法总结)

    一张图带你了解Python,更快入门, 一张图认识Python(附基本语法总结) Python基础语法总结: 1.Python标识符 在 Python 里,标识符有字母.数字.下划线组成. 在 Pyt ...

  10. python解释器在语法上不支持 编程方式-python解释器在语法上不支持什么编程方式_后端开发...

    python程序的两种运行方式是什么_后端开发 python程序的两种运行方式是:1.使用REPL模式运行,REPL模式即读取-计算-打印-循环的模式,借助的工具是IDLE(python集成开发环境) ...

最新文章

  1. OpenCV中Mat数据结构使用举例
  2. CNN-RNN结合的3D物体识别分类
  3. 感知机模型[神经网络入门]
  4. OpenCV通过形态学操作提取水平线和垂直线
  5. 剑指offer(23)二叉搜索树的后序遍历序列
  6. 都江堰很美-佩服古人_Crmhf的一天
  7. 【ArcGIS风暴】ArcGIS添加超链接的两种方法详解
  8. js获取自定义属性的值
  9. Ubuntu的LAMP与相关软件安装设置
  10. as导入项目没有gradle文件夹_【Studio】导入其他项目卡死
  11. Spring MVC 中集成 Apache Shiro 安全框架
  12. C语言libiconv编程,libIconv.lib编码库的生成和使用
  13. 正高、正常高、大地高
  14. し: make jianjie的文本网页
  15. 用JQuery实现简单计时答题游戏
  16. 小呆学数据分析——用duplicated/drop_duplicates方法进行重复项处理
  17. Ubuntu16.04中文输入法安装初战
  18. 如何设计一个项目的数据库?
  19. 如何回答「为什么想来我们公司」【面试核心问题2】
  20. Oracle取排序的第五条数据,OVER(PARTITION BY)函数介绍 【oracle中按A分组按B排序,再取B中第一条数据的查询】...

热门文章

  1. 2021年中国外卖行业发展现状、市场竞争格局及未来发展趋势分析:美团外卖市场份额持续提升[图]
  2. ResHacker 3.5 汉化绿色版
  3. 论文翻译:Associative Embedding:End-to-End Learning for Joint Detection and Grouping
  4. 写论文引用参考文献详细教程
  5. Cocos2d-x制作跨平台太空射击游戏
  6. ADS1115驱动程序
  7. 现代新赛道(现代教育)高考日语主编董文彦
  8. Java多线程系列--【JUC集合02】- CopyOnWriteArrayList
  9. NIOS系统固化方法汇总(详细步骤)
  10. 单层石墨烯结构图matlab,CST中如何建立单层石墨烯模型