指针

算法解析:通过快慢指针判断链表是否存在环并找到环的起点

梦想与她 提交于 2020-03-09 06:17:11
问题描述 给定一个单向链表,请判断该链表是否存在环;如果存在的话,请找到环的起点。 重要 注1:为了描述方便,后文中除非特殊指定,否则将“ 单向链表 ”简称为“ 链表 ” 注2:本文以包含头结点的链表为例,如果是一个不含头结点的链表,因为起始位置不同,所以一些变量的定义会受到影响,但不影响本文讨论的解题方法 问题分析 一般情况下,一个链表存在一个 尾结点 ,该结点的 next 指针为空。然而,当一个链表的 尾结点 指向了之前的某个前序结点时,链表就出现了“ 环 ”: 本题就是要判断一个给定的链表是否存在环,并找到环开始的位置。 注:严格来说,有环链表是没有尾结点的,因为不存在“ 最后一个结点 ”。但后文为了描述方便,仍然将指向环首结点的这个结点称为 尾结点 。 解题方案 可以通过 快慢指针 来判断一个链表是否有环。 什么是快慢指针 在一个链表的头结点处设置两个指针 slow 和 fast 并同时向前移动,规定 slow 每次移动一个结点, fast 每次移动两个结点,这就是快慢指针。 如何利用快慢指针判断链表存在环 如果链表不存在环,则肯定存在一个结点,其 next 指针为空,所以,只要 fast 在移动过程中遇到了空结点,则证明链表不存在环。 如果链表存在环,那么,因为 fast 移动速度比 slow 要快,所以,一定会在某些时刻, fast 会从后面追上 slow 。问题在于:

如何使用C++智能指针,及注意事项。

核能气质少年 提交于 2020-03-09 06:11:15
1、基础介绍 a、智能指针是 行为像指针的类对象 ,其包含一些功能有助于处理动态内存。 b、使用智能指针需包含 <memory> 头文件。 c、四个智能指针分别为: auto_ptr:C++11抛弃,用unique_ptr代替。 unique_ptr:C++11新增, 建立所有权,只能一个指针拥有指定对象,赋值操作会转移对象所有权 。 shared_ptr:C++11新增, 建立引用计数,可以多个指针拥有一个对象,计数器归零时才调用delete 。 weak_ptr:C++11新增,没了解。 2、如何定义智能指针对象 只能用于堆上内存 # include <memory> # include <string> 1 、 auto_ptr < double > a1 = new double ( 5.2 ) ; double * a2 = new double ; a1 = a2 ; // 错误,智能指针的构造函数只接受普通指针作为参数, // 指针到对象的赋值类型不匹配。 2 、 int b1 = 123 ; unique_ptr < int > b2 ( & b1 ) ; // 错误,只能用于堆上内存 std :: string abc = "asjdhasj" ; unique_ptr < std :: string > b3 ( & abc ) ; //错误,b3过期时, //

【JVM.1】java内存区域与内存溢出

你离开我真会死。 提交于 2020-03-09 05:48:09
鲁迅曾说过:Java与C++之间有一堵由内存动态分配和垃圾收集技术所围成的“高墙”,墙外面的人想进来,墙里面的人想出去。 一.虚拟机内存分布 Java虚拟机在执行Java程序的过程中会把它所管理的内存划分为若干个不同的数据区域。 1.  程序计数器(Program Counter Register)   程序计数器是一块较小的内存空间,它可以看作是当前线程所执行的 字节码的行号指示器 。    由于Java虚拟机的多线程是通过线程轮流切换并分配处理器执行时间的方式来实现的,一个处理器都只会执行一条线程中的指令。因此,为了线程切换后能恢复到正确的执行位置,每条线程都有一个独立的程序计数器,各个线程之间计数器互不影响,独立存储。称之为“线程私有”的内存。程序计数器内存区域是虚拟机中唯一没有规定OutOfMemoryError情况的区域。 2.  Java虚拟机栈(Java Virtual Machine Stacks)   java虚拟机也是 线程私有 的,它的生命周期和线程相同。虚拟机栈描述的是Java方法执行的内存模型:每个方法在执行的同时都会创建一个栈帧(Stack Frame)用于存储 局部变量表、操作数栈、动态链接、方法出口 等信息。   咱们常说的堆内存、栈内存中,栈内存指的就是虚拟机栈。 局部变量表存 放了编译期可知的各种 基本数据类型 (8个基本数据类型)、 对象引用

JVM运行时数据区域

三世轮回 提交于 2020-03-09 05:17:22
一、运行时数据区域 相应脑图 程序计数器 记录正在执行的虚拟机字节码指令的地址(如果正在执行的是本地方法则为空)。 Java 虚拟机栈 每个 Java 方法在执行的同时会创建一个 栈帧 用于 存储局部变量表 、 操作数栈 、 常量池引用等信息 。 从方法调用直至执行完成的过程,就对应着一个栈帧在 Java 虚拟机栈中入栈和出栈的过程。 对于执行引擎来说,活动线程中,只有栈顶的栈帧是有效的,称为 当前栈帧 ,这个栈帧所关联的方法称为 当前方法 。 执行引擎所运行的所有字节码指令都只针对当前栈帧进行操作。 操作数栈: 一个后进先出(Last-In-First-Out)的操作数栈,也可以称之为表达式栈(Expression Stack)。 操作数栈和局部变量表在访问方式上存在着较大差异,操作数栈并非采用访问索引的方式来进行数据访问的, 而是**通过标准的入栈和出栈操作来完成一次数据访问**。 每一个操作数栈都会拥有一个明确的栈深度用于存储数值,一个32bit的数值可以用一个单位的栈深度来存储,而2个单位的栈深度则可以保存一个64bit的数值, 当然操作数栈所需的容量大小在编译期就可以被完全确定下来,并保存在方法的Code属性中。 可以通过 -Xss 这个虚拟机参数来指定每个线程的 Java 虚拟机栈内存大小: java -Xss512M HackTheJava 该区域可能抛出以下异常:

Java内存区域

耗尽温柔 提交于 2020-03-09 05:15:53
运行时数据区域: 程序计数器 : 通过改变计数器的值来选取下一条字节码指令,为了线程切换后能恢复到正确的执行位置,每条线程都有一个独立的程序计数器,即“线程私有”如果线程执行的是Java方法,那么计数器记录的是正在执行的虚拟机字节码指令的地址,如果是native方法,则计数器的值为空,此区域没有OutOfMemoryError情况。 Java虚拟机栈 : 线程私有,描述Java方法执行的内存模型,每个方法都会创建栈帧,用于存储局部变量表、操作数栈、动态链接、方法出口等。。方法调用直至完成,对应栈帧入栈到出栈。局部变量表内存空间在编译期间完成分配,运行期间不会改变其大小。线程请求栈的深度大于所允许的深度,则抛出StackOverflowError异常;如果扩展时无法申请到足够的内存,就抛出OutOfMemoryError异常。 设置本地方法栈大小-Xoss(其实无效,应使用后面的),栈容量只由-Xss设定。 单个线程下,抛出的都是StackOverflowError。 如果是建立过多线程导致的内存溢出,可以通过减少最大堆和减少栈容量(每个线程被分配到的栈大小)来换取更多的线程。 本地方法栈 : 执行Native方法,会有StackOverflowError和OutOfMemoryError异常。 Java堆 : jvm中最大的一块,线程共享,唯一目的是存放对象实例

面试题之JVM内存区域

余生颓废 提交于 2020-03-09 05:15:40
1、Java内存区域(运行时数据区域):   jdk1.8之前:虚拟机运行内存分栈、堆和方法区这几种。 栈:虚拟机栈、本地方法栈、程序计数器。(线程私有,每个线程都拥有各自的) 程序计数器:一块比较小的内存空间,可以看做是当前线程所执行的字节码的行号指示器。主要有2个作用: 字节码解释器通过改变程序计数器来依次读取指令,从而实现代码的流程控制,如:顺序执行、选择、循环、异常处理。 在多线程的情况下,程序计数器用于记录当前线程执行的位置,从而当线程被切换回来的时候能够知道该线程上次运行到哪里了。 注意:唯一一个不会出现OutOfMemoryError的内存区域,它的生命周期随着线程的创建而创建,随着线程的结束而死亡。 Java虚拟机栈:生命周期与线程相同(随着线程创建而创建,随着线程死亡而死亡),描述的是Java方法执行的内存模型,每次方法调用的数据都是通过栈传递的。Java内存大概就是堆内存和栈内存,栈是虚拟机栈或是虚拟机栈中局部变量表部分。(实际上,Java虚拟机栈是由一个个栈帧组成,每个栈帧中都拥有:局部变量表、操作数、动态链接、方法出口信息) 局部变量表主要存放了编译器可知的各种数据类型 (boolean、byte、char、short、int、float、long、double)、 对象引用 (reference类型,不同于对象本身,可能是指向一个代表对象起始地址的引用指针

const pointers

[亡魂溺海] 提交于 2020-03-09 00:36:20
1 指针 p对应的地址是常量,但是里面存放的data不是常量 2 地址里存放的data是常量,但是地址不是常量 3 地址和指针都是常量 来源: https://www.cnblogs.com/focusonoutput/p/12445996.html

DS博客作业02-线性表

一曲冷凌霜 提交于 2020-03-08 23:22:33
0.PTA得分截图 1.本周学习总结 1.1 总结线性表内容 什么是线性表? 定义: 线性表是具有相同特性的数据元素的一个有限序列。 线性表一般表示: (a1,a2,a3...ai..an) 这里a1为表头元素,an为表尾元素。 线性表特征: 1.元素个数n——表长度; n=0——空表 2.1<i<n时 a[i]的直接前驱是a[i-1],a[1]无直接前驱 a[i]的直接后继是a[i+1], a[n]无直接后继 3.元素同构,且不能出现缺项 线性表的抽象数据类型描述 ADT List { 数据对象D={ai|ai∈Elemset, i=1,2, . n, n≥0} 数据关系: R={<ai-1, ai>|ai-1,ai∈D, i=2, .., n} 基本操作: InitList (&L) :构造一个空的线性表L DestroyList (&L) :销毁线性表L占用内存空间 ListEmpty(L):若线性表L为空表,则返回TRUE,否则返回FALSE ListLenght(L):返回线性表L数据元素个数 GetElem(L, i, &e):用e返回线性表L中第i个数据元素的值 LocatElem(L,e):返回L中第一个值域与e相等的逻辑位序。若这样的元素不存在,则返回值为0。 ListInsert(&L, i,e) : ListDelete(&L, i, &e) : } /

c++ primer 第二章要点

爱⌒轻易说出口 提交于 2020-03-08 22:15:54
c++ primer 第二章要点 2.1 基本内置类型 2.1.1 算数类型 c++定义了包含 算数类型 和 空类型 的基本数据类型 算数类型包含:1.字符;2.整形数;3.布尔值;4.浮点数 空类型在函数不返回任何值时使用空类型作为返回类型 算数类型尺寸 char的大小和一个机器字节一样,一个字节8比特 使用int执行整数运算,超过int范围使用long long 执行浮点数选用double,float单精度精度不够 2.1.2 类型转换 带符号数在表达式中同时出现无符号数时会自动的转化为无符号数,影响结果正确性 double pi = 3, pi = 3.0 2.1.3 字面值常量 整形和浮点型字面值,字符和字符串字面值 单括号char型,双括号string型 编译器在每个字符串的结尾处加一个空字符‘\0’,所以字符串的实际长度比字面值多1 通过添加前缀或后缀可以改变字面值类型 布尔值字面值(true,false)和指针字面值(nullptr) 2.2 变量 2.2.1 变量定义 int sum = 0, value, units_sold = 0 定义于函数体内部的变量将不被初始化 2.2.2 变量声明和定义的关系 声明规定了变量的类型和名字,定义申请了存储空间。 如果想要声明变量,需要在变量名前加 extern 并且不进行初始化 如果想在多个文件中使用同一个变量