![](https://img-blog.csdnimg.cn/20201014180756754.png?x-oss-process=image/resize,m_fixed,h_64,w_64)
记录
文章平均质量分 52
爱拍球的程序圆
保持简单,不管是生活还是程序。编程、打球、阅读,生活中有这三件事不是已经很足够了吗?
展开
-
关于sizeof和memset/memcpy的一些事
首先,sizeof是一个操作符,不是一个函数,但是当操作数为类型名称时需要用小括号将类型名称包围起来(操作数为变量时不需要),这一规则使得sizeof看起来想一个函数一样。其次如果sizeof的操作数为静态数组名时,得到的结果是整个数组所占的空间大小(以byte为单位),但是如果操作数动态数组时,得到只是一个指针变量所占的用的大小(我的机器上是4byte)。这是因为数组和指针实际上是两个不同的对象(原创 2015-04-09 09:42:15 · 1398 阅读 · 0 评论 -
《Effective C++》重点摘要(三)
《Effective C++》第三章:资源管理以对象管理资源。一份资源,可能是一片内存,可能是一个锁,当客户申请后需要手动释放才是合理的,那么最好在获得这份资源的时候,就立刻把它放到一个对象里(RAII技术),然后在对象的析构函数里释放它。这样释放操作就不会被遗忘了,并且,就算在使用资源类的语境中有语句抛出异常,也能确保资源得到正确的释放。在资源管理类中小心coping行为。有的资源是不支持co原创 2015-04-21 10:20:03 · 582 阅读 · 0 评论 -
《Effective C++》重点摘要(二)
《Effective C++》第二章:构造/析构/赋值运算C++默认编写的函数。C++编译器如果没有发现以下函数,就会为类生成一份默认版本的: 1) default构造函数 2) default析构函数 3) copy构造函数 4) copy assignment操作符(=运算符) 前两个函数并不总是产生,它只在编译器需要的时候才产生出来。后两个函数只保证以bitwise语义拷贝原创 2015-04-21 10:10:40 · 582 阅读 · 0 评论 -
《Effective C++》重点摘要(一)
开篇的话这个星期不再发布关于数据结构的博客,想把半个月来看的书做一些总结,整理整理,第一本就是《Effective C++》。第一次看这本书是一年多前,准备考研复试的时候,随后陆陆续续,这个月再来看算是第三遍了吧,之前没有看过《深度探索C++对象模型》,所以有的地方看得不是很透彻(现在有的地方也看得不透,但是比以前好点了)。还有另一本书就是《深度探索C++对象模型》,看第二遍,吸收得更容易了,看书总原创 2015-04-21 09:53:41 · 727 阅读 · 0 评论 -
《More Effective C++》重点摘要二:操作符
对定制的“类型转换函数”警觉。两种函数允许编译器执行类型转换:1)单变量constructors;2)隐式类型转换操作符。第一种函数可以是明确只有一个单变量的constructor,也可以是拥有除第一个参数外其他参数有默认值的constructor。当编译器发现需要某个类型的对象而实际得到的对象类型不匹配时,它会尽力搜索一种能够执行转换的方式,这个时候以得到的实际类型对象为参数的单变量constru原创 2015-04-26 09:41:11 · 615 阅读 · 0 评论 -
每日一题24:堆
本文记录了使用C++模板实现了堆的基本操作,对于其他一些有用操作如IncreaseKey和DecreaseKey等则没有实现,这是因为使用模板把最小堆和最大堆揉在一起,对Key的增减我还没有找到比较好的处理方式,而现在写这个堆数据结构主要是因为在Hoffman树算法需要,基本操作已经够用了。 堆是一棵完全二叉树,所谓完全二叉树就是一棵从上倒下,从左到右依次填满每一个位置的二叉树,除了最后一层节点没原创 2015-05-14 14:59:16 · 671 阅读 · 0 评论 -
每日一题27:并查集
并查集是一种支持合并于查找的结构,主要用于快速将一个集合与另一个集合合并,查找某个元素所在的集合。假设有N个元素,编号为0到N-1,那么可以构造一个同样大小的整数数组A,A中每个元素存放对应集合元素所属类的编号,查找一个元素所在的集合时,到A中检查对应下标的元素就知道了一个所属的集合。当要合并时,把涉及的元素在A中对应下标的元素设为合并后的集合标识,原创 2015-05-24 10:23:54 · 456 阅读 · 0 评论 -
每日一题29:最小生成树
最小生成树是指包含图中所有的顶点而又没有环并且所有边的权值最小的子图,由于这张图没有环,所以就是一棵树。比较流行的两种找到最小生成树的算法有Kruscal算法和Prim算法。本文在代码注释里写明算法的原理和实际计算步骤,然后贴出两种算法运行的结果示例,最后证明算法的正确性。原创 2015-05-29 08:23:03 · 919 阅读 · 3 评论 -
每日一题28:图的基本操作
本文记录了基于邻接表表示的有向有权图的基本操作。邻接表表示的图的结构就是用一个散列表存储图的节点,而每个节点后面跟着从节点出发的所有边的集合,这些边用链表连接起来,所以在这样的图中寻找一个节点发出的边是容易的,但是寻找进入一个节点的边是困难的,需要遍历所有的边。删除一条边也比较容易,删除一个节点则需要寻找与该节点相关的所有边,并将这些边也删除。#ifndef _NOWEIGHTGRAPH_H_#d原创 2015-05-28 19:14:57 · 685 阅读 · 0 评论 -
每日一题30:拓补排序
所谓拓补排序就是确定图中节点的一种顺序,使得某些在别的节点访问之前不能访问到的节点排在后面。所以该算法的核心是每一步选择一个没有入度的节点,因为没有入度意味着该节点没有前驱,得到一个节点后,就把以新得到的节点为起点的边去除,从剩下的节点重复前面的过程直到所有节点都排好序或找不到一个不具有入度的节点为止。但是实际实现中不必真的删除边,只需要记录每个顶点的入度数,删除边的操作就可以用递减相关顶原创 2015-05-29 09:04:00 · 791 阅读 · 0 评论 -
每日一题32:排序
排序概述排序用途广泛,比如为数据库查询结果按时间排序,最小生成树算法中对边按权重排序,背包问题中对物品按大小排序等等。排序算法有很多,本文主要记录了冒泡排序、插入排序、快速排序、选择排序、堆排序、归并排序等几种比较流行的算法。冒泡排序 //冒泡排序,对数组做n-1趟扫描,每一趟把未就位的元素中的最大的元素 //放到他正确的位置上,每一趟扫描从输入数组第一个元素开始,依次原创 2015-05-31 08:41:38 · 1152 阅读 · 8 评论 -
每日一题31:图的遍历
算法概述图的遍历是指访问图中每个节点一次。图的遍历方式主要有两种,一种是深度优先,即能走多远就先走多远的遍历方式,这就意味着,对于每个节点的遍历完后,下一个访问的节点应该是他的邻接点,而不是兄弟节点。另一种方式是深度优先的方式,这是一种分层遍历,对于没一个节点访问完后,就访问它的兄弟节点,而不是优先考虑邻接顶点。深度优先算法使用递归实现比较直观,而广度优先遍历则需要一个栈辅助,和分层遍历一棵二叉树的原创 2015-05-30 10:55:27 · 1031 阅读 · 0 评论 -
《More Effective C++》重点摘要一:基础议题
仔细区别pointers和references。指针和引用有些相似,他们本身都是对存在于某个地方的对象(不是指class)的指示,但是他们有着本质的区别。指针变量存储所指对象的地址,所指的对象可以是null,只要可以寻址就行。而引用是某个已经存在对象的别名,所以不可以先声明一个引用,经过一段时间(代码)后让它指向某个对象。最好使用C++转型操作符。C++提供了自己的四种转型操作符: 1) st原创 2015-04-24 15:13:40 · 674 阅读 · 0 评论 -
《Effective C++》重点摘要(八)
《Effective C++》第八章:定制new和delete了解new-handler的行为。new和delete不是函数,是申请和释放内存的操作符。当new提出获得内存申请失败时会发生什么?老旧的编译器是返回null指针。现在呢,如果申请失败,会先调用一个错误处理函数,那就是new-handler。这就像一个回调函数,系统有一个默认的,用户也可以自行编写一个错误处理函数并使用set_new_h原创 2015-04-24 08:43:26 · 586 阅读 · 0 评论 -
计算机科学箴言集
这是摘抄自《编程珠玑II》第六章的一些比较有趣的话,加上了一些自己的感想或理解。编码篇回归测试能将测试区间减半。 —Larry Bernstein,贝尔通信研究院Π秒就是一个纳世纪。 —Tom Duff,贝尔实验室如果还没想清楚,就用蛮力算法吧。(自己想了之后,蛮力之前,请别人帮自己想想)原创 2015-03-29 09:38:31 · 684 阅读 · 0 评论 -
《Effective C++》重点摘要(五)
《Effective C++》第五章:实现尽可能延后变量定义式的出现时间。只有变量在恰好要使用之前定义,程序的可读性往往会得到提高,因为这样不容易忘记变量说代表的意思。另一方面,这样做可以提高程序性能,如果不需要一个变量时却要为它分配、释放空间,调用构造、析构函数,获取、释放资源……这,真是太浪费了。补充一点,声明式并不会做这些事情,所以可以考虑用声明式替换定义式以尽量延后变量的定义。尽量少做转原创 2015-04-22 07:48:54 · 606 阅读 · 0 评论 -
《Effective C++》重点摘要(四)
《Effective C++》第四章:设计与声明让接口容易被正确使用,不易被误用。一个接口由返回类型、接口名称、和参数列表组成,为了让接口容易被正确的使用,需要小心设计返回类型,最好是简单、直接、自然。接口名称选择很重要,做到简单、达意、无歧义。参数列表形参类型需要身份小心,如果能防范非法输入,尽力为之,形参名也尽可能做到同接口名称一样的标准。另外请保持命名习惯的一致性也能收到奇效。设计clas原创 2015-04-21 15:20:03 · 593 阅读 · 0 评论 -
每日一题14:数组与链表组合方案下的Josephus问题
愚人节与自己开了个很大的玩笑,几天没写程序,今天继续!Josephus问题是说N个人围成一个圈传热土豆,先约定一个数M,当传递了M次的时候拿着土豆的人出局,然后将土豆给出局人的下一个人,游戏继续,直到最后只剩下一个人,求出局人的序列(按出局顺序排列)。 这个问题可以用数组实现,但是需要标记代表出局人的元素,并且没遍历一个元素就要检查该元素是否已被标记为出局,这样程序运行时间必然会变慢。另一种方式是原创 2015-04-04 09:38:18 · 641 阅读 · 0 评论 -
《Effective C++》重点摘要(六)
《Effective C++》第六章:继承与面向对象设计确定你的public继承塑模出is-a关系。student is a person,所以student可以public继承自person。概念上,正方形是长方形,但是如果让square继承自rectangle呢,square需要像rectangle那样具有长和宽两个成员变量吗?如果是,每次改变正方形的宽的时候,也要改变正方形的长,这很奇怪不是原创 2015-04-22 14:21:39 · 572 阅读 · 0 评论 -
宁以non-member且non-friend替换member函数
这样做的第一个理由是增加封装性,咳咳,这听起来有点矛盾,因为non-member且non-friend成员函数要想处理某个类中的数据的话,就得看到(即能访问)该类中的数据,那么数据就得是public的。这明显破坏了封装。嗯,解释一下,不是每个函数都要明确看到数据才能处理,它可以调用类中的一序列public函数来完成任务,这些public函数可以明确地看到类中的数据,如果我们把调用他们的函数作为mem原创 2015-04-22 19:28:31 · 764 阅读 · 0 评论 -
未完成的2014
说过去了一年,总感觉不管手上有什么事,都是要告一段落的时候了,可是当一月一日来临的那天,我还在学校里准备即将到来的考试,而回家的票定在了二月八号,所以在我的观念里,这一年还没过完,我的2014延伸到现在,并且还要往前走一段才算过去。我的2014的开端自然不是2014年的一月一号,理由同上。却也不是2014年的春节,因为那段记忆比较模糊,在东莞过的年,隐约记得些影子,却也不是很重要的事。我的2014似原创 2015-04-11 12:02:20 · 459 阅读 · 0 评论 -
《Effective C++》重点摘要(七)
《Effective C++》第七章:模板与泛型编程了解隐式接口和编译期多态。面向对象编程总是采用显式地声明一个接口,并在子类中提供特殊的实现,进而实现运行期多态。模板类中的接口往往是隐式的,隐式的意思是,编写模板时,假设需要的接口类T中是存在的,至于实例化模板的类是否真的具有该接口,编译时才知道(如果实例化类型没有实现这些接口,则编译失败)。这正是模板多态的展现方式,由实例化模板的类决定具体的行原创 2015-04-23 15:55:38 · 700 阅读 · 0 评论 -
《Effective C++》重点摘要(九)
《Effective C++》第九章:杂项讨论不要轻忽编译器的警告。严肃对待编译器发出的警告信息。努力在最高警告级别下争取无警告。也不要过度依赖编译器给出的警告信息,不同的编译器给出的警告信息是不一样的,甚至给出警告的点也不一样。让自己熟悉包括TR1在内的标准程序库。让自己熟悉Boost。C++不想Java和C#那样,语言本身就带有很强大的库,所以外部的程序库对于编写C++程序至关重要。俗话原创 2015-04-24 09:16:11 · 620 阅读 · 0 评论 -
每日一题26:求逆序对数目与求和
求逆序对问题与解决方案原理在一个数列中,如果规定从小到大为正序,那么如果排在后面的某个元素比前面的某一个元素小,那么就称这两个数构成一个逆序对,例如,数列5,4,3,2,1中,任一个数都与它前面的数构成逆序对,这个序列中一共就有1+2+3+4=10个逆序对,数列23541中有5个逆序对,那么任给定一个数列,如何知道有多少个逆序对呢?简单的方法是将每个元素与它后面的元素比较,然后就可以累加出总的原创 2015-05-21 20:57:28 · 1370 阅读 · 0 评论