自定义博客皮肤VIP专享

*博客头图:

格式为PNG、JPG,宽度*高度大于1920*100像素,不超过2MB,主视觉建议放在右侧,请参照线上博客头图

请上传大于1920*100像素的图片!

博客底图:

图片格式为PNG、JPG,不超过1MB,可上下左右平铺至整个背景

栏目图:

图片格式为PNG、JPG,图片宽度*高度为300*38像素,不超过0.5MB

主标题颜色:

RGB颜色,例如:#AFAFAF

Hover:

RGB颜色,例如:#AFAFAF

副标题颜色:

RGB颜色,例如:#AFAFAF

自定义博客皮肤

-+
  • 博客(27)
  • 收藏
  • 关注

原创 Android getSystemService原理

这是该类的构造函数,需要解释一下,所以缓存的服务实例对象是存储在context的cached数组中的,另外一个int类型数组gates是表示缓存的每一个服务实例对象的当前状态,因此mCacheIndex就是存储的这个fetcher所指服务实例对象在cached数组中的索引。从开头的实例过程可以看出,每一个服务对象都是lazy initialized,因此可以加快activity的启动速度(我的理解),并且避免了实例化一些并不需要的服务对象,只在真正需要的时候才会实例化。这一步注册很多服务。

2023-08-04 19:05:16 295

原创 shell变量的可见性

修饰符标识,当把一个变量export时,他会把这个变量以key-value的形式添加到当前shell环境中。因此可以被子进程读取到,但是跟普通变量一样父进程读取不到该值。可以被整个脚本或者shell环境访问到,但是也仅此而已。子进程和父进程都访问不到。修饰符标识,只能在脚本的函数或者代码块中被访问,即使在该脚本内也不能访问到。后续谈到进程默认都是shell进程,也就是运行shell的进程。二、bash shell三种可见性级别的变量。

2023-07-22 14:42:47 144

原创 声音如何保存成数字信号

比如,2.1 声道中的 2 指的是左右两个音箱,1 指的是中间一个低音音箱(如图 4 所示)。根据奈奎斯特采样定理在进行模拟 / 数字信号的转换过程中,当采样频率 fs 大于信号中最高频率 fmax 的 2 倍时(fs > 2fmax),采样之后的数字信号才可以完整地保留原始信号中的信息。由图 可知,16kHz 采样率的音频在 8kHz 以上的频谱基本是没有能量的(黑色),也就是说这部分高频的信息由于采样率不够已经丢失了。比如麦克风阵列采集到的原始信号,有多少个麦克风就会有多少个通道的音频信号。

2023-06-15 17:41:48 572

原创 android音频架构以及技术选型

Android 系统在 NDK 层(Native 层提供的 API,即 C 或者 C++ 层可以调用的 API)提供了 2 套常用的音频渲染方法,分别是 OpenSL ES 和 AAudio,它们都是为 Android 的低延时场景(实时耳返、RTC、实时反馈交互)而设计的,下面我们一起来看一下。Android 系统为开发者在 SDK 以及 NDK 层提供了多种音频渲染的方法,每一种渲染方法其实也是为不同的场景而设计的,我们必须要了解每一种方法的最佳实践是什么,这样在开发工作中才能如鱼得水地使用它们。

2023-06-15 17:14:47 2222

原创 程序员自我修养笔记:第12章

第 12章 系统调用原理1.普通应用程序运行在用户态下,唯一进入内核态的方式就是通过系统中断。中断分硬件中断和软件中断,软件中断一般以int 0x80号进入系统中断处理程序。中断号很好,因此一般中断号与系统调用都是1对多的关系。而Linux下的都是通过0x80号中断来触发系统调用。而通过eax传递系统调用号,参数用其他寄存器传递。而中断的触发还伴随着用户栈到内核栈的转变,并且将ss,esp,eflags,cs,ip压入内核栈方便返回用户程序。这一切都是由int通过硬件自动完成。0x80号的中断处

2022-03-01 15:45:38 7636

原创 程序员自我修养笔记:第十一章

第11章 运行库1.一个典型的程序运行步骤如下:系统创建进程后,把控制权交给程序入口,而这个入口称为入口函数或入口点,这个入口往往是运行库中的某个入口函数。入口函数对运行库和程序运行环境进行初始化,包括堆、IO、线程、全局变量构造等等。入口函数完成初始化后,调用main函数正式执行程序主体部分。main函数执行完后,返回到入口函数,入口函数进行清理工作,包括全局变量析构、堆销毁,关闭IO等,然后进行系统调用(__exit)结束进程。2.glibc入口函数glibc的程序入口为_star

2022-03-01 15:44:43 955

原创 程序员自我修养笔记:第十章

第十章 内存1.调用惯例一个调用惯例,一般会规定如下几方面的内容:函数参数的传递顺序和方式:参数的压栈顺序,有些惯例还允许使用寄存器传递参数。站的维护方式:参数的弹出工作是由函数的调用方还是函数本身来完成名字修饰策略函数返回值传递2.堆程序向操作系统申请一块适当大小的堆空间,然后由程序自己管理这块空间。这个程序往往是程序的运行库。3.Linux下的对空间分配方式有两个系统调用,一个是brk(),另外一个是mmap()。brk()就是设置进行数据段(bss+数据段)的结束地址,

2022-03-01 15:43:19 214

原创 程序员自我修养笔记:第九章

第九章 Windows下的动态链接1.相当于Linux下的共享库,Window系统大量采用dll机制,dll更加强调模块化,经常可以看到Windows平台大量的大型软件都通过升级dll的形式自我完善。2.基地址和RVA当一个pe文件被装载时,其进程地址空间的起始地址就是基地址,每个文件都有一个优先装载地址,位于文件头中的Image Base。通常可执行文件的Image Base不会被占用,因为它总是第一个被装载的文件,dll文件可能会因为被其他已装载的dll文件而进行Rebasing。RVA

2022-03-01 15:41:19 7551

原创 程序员自我修养笔记:第八章

第八章:Linux共享库的组织1.共享库版本不同,可能引起ABI发生变化,从而影响程序的正常运行。因此各个系统会有自己的一套共享库版本命名规则。Linux的为libname.so.x.y.zx:主版本号,y:次版本号,z:发布版本号不同主版本之间共享库差异大,互不兼容。次版本之间仅是添加了新的符号,互相兼容。发布版本之间修改了接口的bug,互相兼容。2.程序依赖的共享库由.dynamic段指出,若指出完整版本(主次发布都有)的共享库名字,则每次更新共享库必须保存之前的版本,会造成磁盘和内存(会

2022-03-01 15:38:42 7741

原创 目标和问题

目标和」,难度为「中等」。Tag : 「DFS」、「记忆化搜索」、「背包 DP」、「01 背包」给你一个整数数组 nums 和一个整数 target 。向数组中的每个整数前添加 ‘+’ 或 ‘-’ ,然后串联起所有整数,可以构造一个 表达式 :例如,nums = [2, 1] ,可以在 2 之前添加 ‘+’ ,在 1 之前添加 ‘-’ ,然后串联起来得到表达式 “+2-1” 。返回可以通过上述方法构造的、运算结果等于 target 的不同 表达式 的数目。282.给表达式添加运算符给定一个仅包含数.

2021-10-16 10:41:57 90

原创 字符串哈希.Ranbin-karp

Repeated DNA SequencesThe DNA sequence is composed of a series of nucleotides abbreviated as ‘A’, ‘C’, ‘G’, and ‘T’.For example, “ACGAATTCCG” is a DNA sequence.When studying DNA, it is useful to identify repeated sequences within the DNA.Given a stri.

2021-10-08 13:06:26 172

原创 lc算法:随机篇

按权重随机选择给定一个正整数数组 w ,其中 w[i] 代表下标 i 的权重(下标从 0 开始),请写一个函数 pickIndex ,它可以随机地获取下标 i,选取下标 i 的概率与 w[i] 成正比。法1:前缀和+二分用 Rand7() 实现 Rand10()根据平均生成1-7的API实现平均生成1-10的API法:根据两次生成的值以二维矩阵的形式采用拒绝采用的算法.........

2021-09-05 15:09:12 676

原创 剑指offer:数组最小k个数

面试题 17.14. 最小K个数法1:维护k大小的最大堆法2:快排

2021-09-03 19:49:32 58

原创 lc算法题:双指针

反转字符串中的元音字母编写一个函数,以字符串作为输入,反转该字符串中的元音字母。

2021-08-19 08:37:09 81

原创 lc算法题:动态规划dp

优美的排列假设有从 1 到 N 的 N 个整数,如果从这 N 个数字中成功构造出一个数组,使得数组的第 i 位 (1 <= i <= N) 满足如下两个条件中的一个,我们就称这个数组为一个优美的排列。条件:第 i 位的数字能被 i 整除i 能被第 i 位上的数字整除现在给定一个整数 N,请问可以构造多少个优美的排列?法1:状态dp出界的路径数给你一个大小为 m x n 的网格和一个球。球的起始坐标为 [startRow, startColumn] 。你可以将球移到在四个方向上.

2021-08-16 19:56:28 206

原创 找[1,n]范围内数字k的个数

lc233. 数字 1 的个数法1:找规律+组合注意k=0的特判

2021-08-13 05:17:11 275

原创 图:找环的算法题

安全点的定义:有向图中,若点的出线中没有在环中或连接到环中,则为安全点。算法,找出图中安全点的列表。lc802方法1:传统dfs+三色标志提高效率方法2:反向图+拓扑排序在环状数组中找环(忽略自环)lc457法1:快慢指针(类似:lc141 环形链表)法2:拓扑排序判断环...

2021-08-07 17:16:53 620

原创 图论:求遍历图最短路径

lc847bfs+状态压缩 求图中任一结点开始访问全部结点的最短路径

2021-08-06 16:48:14 521

原创 dfs+三色着色

安全点的定义:有向图中,若点的出线中没有在环中或连接到环中,则为安全点。算法,找出图中安全点的列表。lc802方法1:传统dfs+三色标志提高效率方法2:反向图+拓扑排序

2021-08-05 16:17:14 169

原创 有序集合的一些感想

前言有序集合的思想本质上是二分的思想,即给定一个值(查找值),在一个有序集合中找出()(第一个)满足条件的的元素(即目标元素)。但是很多时候集合是无序的,因此我们需要维护一个有序集合来找出目标元素。比如,我们要想在一个无序的数组中找出一个与查找值相等的元素,则我们会联想到将当前数组排序,即维护一个有序集合,在通过二分的思想查找目标元素,此时时间复杂度从依次遍历的O(n)降低到了O(nlogn),而这也是我们引入有序集合的原因之一,即提高时间上的效率。为什么需要有序集合现在我们已一个无序的数组开始下面

2021-04-22 21:32:46 100

原创 二维前缀和的一些整理

前言:二维前缀和是一维前缀和在二维上的体现,要想了解清楚二维前缀和,最好先学习一维前缀和,在逐步深入二维前缀和。因此我们先从一维的开始讲起,另外一个容易忽视的点是,前缀和优化的是查询复杂度,而不是总体的复杂度,请注意这个区别。一维前缀和我们先从问题引入其概念:给定一个整数数组nums,求数组从索引i到j(i≤j)范围内元素的总和。这个问题我们可以很容易的想到一个O(n)的解决方案,从数组左端开始扫描,在扫描索引到i开始,用一个变量依次与每个元素相加,直到指针扫过j。但是有没有更快的方法呢,而

2021-04-22 19:44:45 501

原创 KMP算法的图解

提到这个是想提醒读者,前后缀可能重叠,但不会完全重叠。

2021-04-20 19:41:30 308

原创 最长回文子串

最长回文子串难在初始化边界和填表方式。public class Solution{ public int longestPalindrome(String s) { int n = s.length(); int[][] dp = new int[n][n]; //dp[i][j]为s[i...j]是否为回文串 int ret = 1; //最长回文子串长度为dp二维数组中dp[i][j]为真时i,j距离最大值 //最长回文串难在边

2021-04-03 12:49:18 67

原创 非比较排序

1.计数排序1.先是将数组映射到一个presum数组上,每个元素presum[i]的值为i的出现次数。2.在通过一次遍历将presum数组变为前缀和数组,此时presum[i]的值的含义变为:小于等于i的数有几个3.根据presum即可得知原数组每个元素在排序会后所对应的位置,用一个temp数组保存结果,在复制回原数组。计数排序原理解释链接...

2021-04-02 22:34:57 858

转载 C++ upper_bound()函数

C++ lower_bound()》一节中,系统地介绍了 lower_bound() 二分法查找函数的功能和用法,在此基础上,本节再讲解一个功能类似的查找函数,即 upper_bound() 函数。upper_bound() 函数定义在头文件中,用于在指定范围内查找大于目标值的第一个元素。该函数的语法格式有 2 种,分别是://查找[first, last)区域中第一个大于 val 的元素。ForwardIterator upper_bound (ForwardIterator first, For

2021-03-30 14:19:23 11292 3

原创 秒懂希尔排序

秒懂希尔排序希尔排序(优化后的插入排序)是把序列按下标的增量分组,对每组使用直接插入排序;随着增量的逐渐减少,各组元素越来越多,当增量减至1时,整个序列恰好分为1组,将整个组(序列))插入排序后算法便终止。此处增量采用的是朴素增量。因此最坏时间复杂度比直接插入排序时间复杂度更大。vector<int> sortArray(vector<int>& nums) { int n = nums.size(), gap = n / 2, j;

2021-03-30 12:23:36 79

转载 析构函数

C++析构函数详解析构函数(destructor)是成员函数的一种,它的名字与类名相同,但前面要加~,没有参数和返回值。一个类有且仅有一个析构函数。如果定义类时没写析构函数,则编译器生成默认析构函数。如果定义了析构函数,则编译器不生成默认析构函数。析构函数在对象消亡时即自动被调用。可以定义析构函数在对象消亡前做善后工作。例如,对象如果在生存期间用 new 运算符动态分配了内存,则在各处写 delete 语句以确保程序的每条执行路径都能释放这片内存是比较麻烦的事情。有了析构函数,只要在析构函数中调用 d

2020-11-21 14:37:00 226

公众号又又又又又又又又又又改版了

公众号又又又又又又又又又又改版了

2024-05-11

空空如也

TA创建的收藏夹 TA关注的收藏夹

TA关注的人

提示
确定要删除当前文章?
取消 删除