数据结构基本概念
对于数据结构,官方没有统一概念,以下是三个经典著作中数据结构的定义
数据结构是数据对象,以及存在于该对象的实例和组成该实例的数据元素之间的各种联系。
这种联系可以通过定义相关的函数来给出。 --Sartaj Sahni,《数据结构、算法与应用》
数据结构是ADT(抽象数据类型 Abstract Data Type)的物理实现。
–Clifford A.Shaffer 《数据结构与算法分析》
数据结构(data structure)是计算机中存储、组织数据的方式。通常情况下,精心选择的
数据结构可以带来最优效率的算法。 --中文维基百科
解决问题方法的效率,往往与数据的组织形式,跟空间的利用效率,跟算法的巧妙程度等等有关
数据结构:数据对象在计算机中的组织方式
逻辑结构
物理存储结构
数据对象必定与一系列加在其上的操作相关联,完成这些操作所用的方法就是算法
(数据结构研究逻辑结构和物理结构以及它们之间的相互关系,并对这种结构定义相适应的运算,设计出相应的算法)
抽象数据类型(Abstract Data Type)
数据类型
数据对象集(数 ...
异常处理
异常处理
在程序运行过程中,有些错误是可以预料,但不可回避的,如:
内存空间不足,外存文件被移动到其他驱动,io设备未处理好等系统运行环境造成的错误。
异常存在于程序的正常功能之外,一般要求程序立即处理。因此,需要考虑一种方法做到部分功能可以允许用户排除环境错误,继续运行程序,部分功能可以给出适当的同时信息。c++的异常处理机制,使得异常的引发和处理不必在同一个函数当中,这样底层的函数可以着重于解决具体问题,不需要过多考虑对异常的处理,而上层的调用者可以在适当的位置设置对不同类型异常的处理,即异常引发和处理不在同一个函数,下层解决问题,上层处理各种异常。异常处理机制提供程序中错误检测与错误处理部分之间的通信。
c++中使用throw(抛出)表达式引发(抛出)异常条件,并以try catch语句块处理异常,try catch语句块以try(检测)开始,并以一个或多个catch(捕获)结束。在try块中执行的代码所抛出的异常,通常由其中的一个catch子句进行处理。
抛出异常的基本格式为:throw 异常数据
异常数据可以包含任意的信息,可以是int、float、bool等基本 ...
模板
模板
常见的代码重用技术有:
函数,类与对象,继承与派生,多态(函数重载,运算符重载,虚函数,纯虚函数,抽象类等),泛型程序设计
通用的代码需要不受数据类型的影响,并且可以自动适应数据类型的变化,这种程序设计类型称为泛型程序设计。
在c++中,泛型实际是通过参数多态性来实现的,参数化的多态是将程序所处理的对象的类型进行参数化,使同一段程序可以处理不同类型的对象。
值(Value)和类型(Type)是数据的两个主要特征,它们在c++中都可以被参数化
问题:定义一个函数,求两个变量之间的较大值,并且使所有基本数据类型都可以使用这个功能
如果采用函数重载的方法,则需要的函数数量较多,并且除了操作的数据类型不同以外,程序框架是一样的,这使代码显得累赘并且加大维护难度
如果采用宏定义的方法,虽然解决了代码维护的问题,但缺少类型检查,极大增加了出错的可能
此时,c的模板可以解决这一问题,数据类型本身就是一个参数。模板的声明或定义只能在全局,命名空间或类的内部进行,即不能在局部范围,函数内进行,如不能main()内声明或定义一个模板。
c模板非常重要,整个标准库几乎都是使用模板来开发的,STL ...
多态性与虚函数
多态
多态是面向对象编程的主要特征之一
基类指针/引用可以按照基类的方式来做事,也可以按照派生类的方式来做事,它有多种形态,或者说有多种表现方式,这种现象即为多态
简单而言,多态就是用相同或相似的方法进行处理而得到的是不同的结果
即使用方法看起来没有区别,但实现的功能是完全不同的,达到一个界面,多种实现的效果
多态分类
多态分为两类:编译时的多态,运行时的多态
编译时的多态包括:函数重载,运算符重载
运行时的多态:虚函数实现 (动态绑定)
继承和动态绑定在两个方面简化了程序:
可以容易地编写与其他类相似但又不相同的新类
可以容易地编写忽略这些相似类型之间区别的程序
许多应用程序的特性可以用一些相关但略有不同的概念描述,面向对象编程与这种应用非常匹配。通过继承可以定义一些类型,可以模拟不同种类,而通过动态绑定可以编写程序,使用这些类而又忽略与具体类型相关的差异。
继承和动态绑定在概念上非常简单,但对于如何创建应用程序以及对于程序设计语言必须支持的特性,含义深远。
面向对象编程的关键思想是多态性,因为在许多情况下可以互换地使用派生类型或基类型的许多形态,所以称通过继承而相关联 ...
运算符重载
运算符重载
使用c++编写程序时,不仅要使用基本数据类型,还要设计新的数据类型->类
一般情况下,基本数据类型的运算都是用运算符来表达,语义简单并且直观,如:
int a,b,c;a=b+c;
对于基本数据类型运算的汇编语言实现,其中就隐含着运算符重载的概念,如:
int a,b,c;c=a+b;float a,b,c;c=a+b;
整型加法的汇编代码为:
mov eax,dword ptr[ebp-4]
add eax,dword ptr[ebp-8]
mov dword ptr[ebp-0Ch],eax
实数型加法的汇编代码为:
fld eax,dword ptr[ebp-4]
fadd eax,dword ptr[ebp-8]
fstp dword ptr[ebp-0Ch],eax
虽然都是+,整型和实数型的基本操作指令是不同的,但是对于高级程序语言使用者而言则完全感受不到
这是因为通过对运算符的重载,在底层实现了相关运算的具体操作
如果将运算符直接作用于类对象,编译器将无法识别运算符的语义,因为对类对象的运算并没有提前实现,如:
Complex ret ...
继续
人生最清晰的脚印,往往印在最泥泞的路上。
如果你想拥有从未有过的东西,那你必须去做从未做过的事情。
去做你想做的事情,趁阳光正好,趁现在还年轻!你今日撒下的种子,会在你看不见想不到的某日,悄悄地生根发芽。
【转】大佬事迹
绝大多数的互联网企业,要么是源起于技术咖的一个想法,要么是由技术过硬的人掌舵。
这些人的创业或是成名之路其实相差甚远,但几乎所有人都有一个共同点,就是在初入编程世界时,都给自己定过“至少做十年程序员”、“只想对着电脑写代码”、“至少写十多万行代码”之类的“小目标”。虽然初心的保质期往往不长,但如果连初心都没有,后面的故事自然也不会发生。
网易丁磊,创办网易时的50万元资金是他写了几年代码积攒下来的。成立网易云之后,丁磊还曾梦想在云计算上投入十亿人民币,解放全国千千万万的程序员。
搜狗王小川,在清华读书时,排队看医生还要捧着计算机的书,在搜狗可以花几年时间一级一级组建产品,能让他感到兴奋的事是“有些问题没人能解决,你找到方法解决了”。
京东刘强东,大学主修社会专业,课余时间却自学编程,还用 ASP 写出了第一版的京东。
新浪创始人王志东,自称是“很纯粹的软件工程师”,说程序员的目标就是要实现一个很好很实用的产品。曾创立过四通利方、新浪、点击科技。
“成为一个合格的程序员,怎么也要写个10万到15万行以上的代码,如果连这个量级的代码都没有达到,那说明你还不会写程序” ——周鸿祎
求伯君—— ...
区块链入门了解
因为不久后要组队参加区块链比赛,所以新开了这个系列用于记录一些区块链开放相关的知识
本系列是参考Microsoft区块链开发入门内容整理得来的
什么是区块链?
区块链是一种用于保留记录和执行合同的技术,通过使用加密来确保极难更改以前的历史记录,并且允许参与者通过跟踪共享账本的更改来共享工作流程。
为什么不使用集中式数据库?
下面以一个冰淇淋案例的形式作为后续讨论的基础:
假设你是解决方案架构师,供职于一家生产冰淇淋的乳制品加工公司。你通过供应链接收来自多个牛奶场的未加工牛奶,你的公司将包装好的冰淇淋运输至多个零售商。
运输过程中温度不正确将导致产生食物质量和安全问题,而因为有多个公司负责运输和存储产品,因此很难识别供应链中出错的一方。
因此,你需要创建一个系统,用于快速识别供应链中的问题。
显然,我们可以建立一个集中式数据库,让所有参与者使用它来跟踪运输,实际在许多方案中,集中式数据库都是适当的解决方案。
那么假设我们有一个集中式数据库,该数据库存储有关元素和当前责任方的详细信息。可以让农场主、承运方、工厂和零售商使用同一个集中式数据库。
集中式数据库的优点是可以轻松控制访问权 ...
单继承和多继承、派生类构造析构规则
单继承和多继承
继承分为单继承和多继承
单继承:派生类只有一个直接基类(如:A->B->C)
多继承:派生类有多个直接基类(如:X,Y->Z)
定义单继承派生类的基本格式:
class 派生类名:<继承方式>基类名{继承基类的成员,新添加的成员};
定义多继承派生类的基本格式:
class 派生类名:<继承方式1>基类名1,<继承方式2>基类名2…{继承基类的成员,新添加的成员};
定义的缺省继承方式是私有继承方式
继承关系中构造与析构原则
派生类继承了基类成员,对象中既包含基类成员又包含派生类成员,因此初始化时需要通过构造函数同时初始化全部成员
派生类在构造对象时,先生成自己的基类部分,然后生成自己的成员对象,最后生成自身特有的部分
构造函数、析构函数调用原则
在创建派生类对象时(其实创建组合类的情况类似)
如果派生类没有定义构造函数,则调用基类的无参数的构造函数
如果派生类定义了构造函数,不论是无参数还是带参数,在创建派生类的对象的时候,首先执行基类无参数的构造方法,然后执行自己的构造函数
如果派生类的构造 ...
继承、派生
继承、派生
在自然界中,继承与派生是一种非常普遍的现象
例:猫类,狗类都属于哺乳动物类,具备胎生,哺乳,恒温等哺乳动物的所有性质,同时又具有各自的特有的性质
这是就是继承关系的重要性质,形成继承关系的两个类之间,具有IS_A的关系
继承:一旦指定某种事物父代的本质特征,那么它的子代会自动具有这些性质
继承是一种朴素的可重用的概念
派生:子代可以拥有父代所没有的特性,这是可扩充的概念
继承就是在一个已存在的类基础上建立另一个新的类
已存在的类,称为基类或父类,新建立的类称为派生类
派生类的功能主要通过以下方式来体现:
吸收基类的成员
改造基类的成员
添加新成员
从编码的角度,派生类从基类中以较低的代价换取了较大的灵活性:
派生类可以对继承的属性进行扩展,限制或改变,一旦产生可靠的基类,只需要调试派生类所作的修改即可
在面向对象思想发展的初期,通过继承复用代码曾经被认为是面向对象最重要的目标之一,但遗憾的是,实践中人们发现在开发中滥用继承的话是后患无穷的
这是因为代码中存在一定的耦合性,基类会产生较深的类型继承树,因此常常牵一发而动全身
继承是对类型之间的关系建模,共享 ...