Skip to content

Commit 7e95793

Browse files
committed
update
1 parent df2d625 commit 7e95793

7 files changed

Lines changed: 184 additions & 36 deletions

File tree

AdavancedPart/Crash及ANR分析.md

Lines changed: 15 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -4,9 +4,13 @@
44
## Java Crash流程
55

66
1、首先发生crash所在进程,在创建之初便准备好了defaultUncaughtHandler,用来处理Uncaught Exception,并输出当前crash的基本信息;
7+
78
2、调用当前进程中的AMP.handleApplicationCrash;经过binder ipc机制,传递到system_server进程;
9+
810
3、接下来,进入system_server进程,调用binder服务端执行AMS.handleApplicationCrash;
11+
912
4、从mProcessNames查找到目标进程的ProcessRecord对象;并将进程crash信息输出到目录/data/system/dropbox;
13+
1014
5、执行makeAppCrashingLocked:
1115

1216
创建当前用户下的crash应用的error receiver,并忽略当前应用的广播;
@@ -19,8 +23,11 @@
1923
当1分钟内同一进程未发生连续crash两次时,则执行结束栈顶正在运行activity的流程。
2024

2125
7、通过mUiHandler发送消息SHOW_ERROR_MSG,弹出crash对话框;
26+
2227
8、到此,system_server进程执行完成。回到crash进程开始执行杀掉当前进程的操作;
28+
2329
9、当crash进程被杀,通过binder死亡通知,告知system_server进程来执行appDiedLocked();
30+
2431
10、最后,执行清理应用相关的四大组件信息。
2532

2633

@@ -35,12 +42,15 @@
3542

3643

3744

38-
Native Crash
45+
Native Crash:
46+
47+
- 崩溃过程:native crash 时操作系统会向进程发送信号,崩溃信息会写入到 data/tombstones 下,并在 logcat 输出崩溃日志
48+
49+
- 定位:so 库剥离调试信息的话,只有相对位置没有具体行号,可以使用 NDK 提供的 addr2line 或 ndk-stack 来定位
50+
51+
- addr2line:根据有调试信息的 so 和相对位置定位实际的代码处
3952

40-
崩溃过程:native crash 时操作系统会向进程发送信号,崩溃信息会写入到 data/tombstones 下,并在 logcat 输出崩溃日志
41-
定位:so 库剥离调试信息的话,只有相对位置没有具体行号,可以使用 NDK 提供的 addr2line 或 ndk-stack 来定位
42-
addr2line:根据有调试信息的 so 和相对位置定位实际的代码处
43-
ndk-stack:可以分析 tombstone 文件,得到实际的代码调用栈
53+
- ndk-stack:可以分析 tombstone 文件,得到实际的代码调用栈
4454

4555

4656

AdavancedPart/Java

Whitespace-only changes.

Gradle&Maven/kts.md

Lines changed: 32 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -4,60 +4,72 @@ Gradle 支持使用 Groovy DSL 或 Kotlin DSL 来编写脚本。所以在学习
44

55
所以下面来学习一下这两种语言的差异。
66

7-
1. Groovy 和 Kotlin 的差异
7+
1. Groovy 和 Kotlin 的差异
8+
89
1.1 语言差异
9-
Groovy
10-
Groovy是一种基于 JVM 的面向对象的编程语言,它可以作为常规编程语言,但主要是作为脚本的语言(为了解决 Java 在写脚本时过于死板)。它是一个动态语言,可以不指定变量类型。它的特性是支持闭包,闭包的本质很简单,简单的说就是定义一个匿名作用域,这个作用域内部可以封装函数和变量,外部不可以访问这个作用域内部的东西,但是可以通过调用这个作用域来完成一些任务。
11-
Kotlin
12-
Kotlin 则是 Java 的优化版,在解决 Kotlin 很多痛点的情况下,不引入过多的新概念。它具有强大的类型推断系统,使得语言有良好的动态性,其次是其语言招牌 —— 语法糖,Kotlin 的代码可以写的非常简洁。这使得 Kotlin 不仅做为常规编程语言能大放异彩,作为脚本语言也深受很多开发者喜爱。
10+
11+
Groovy是一种基于 JVM 的面向对象的编程语言,它可以作为常规编程语言,但主要是作为脚本的语言(为了解决 Java 在写脚本时过于死板)。
12+
13+
它是一个动态语言,可以不指定变量类型。它的特性是支持闭包,闭包的本质很简单,简单的说就是定义一个匿名作用域,这个作用域内部可以封装函数和变量,外部不可以访问这个作用域内部的东西,但是可以通过调用这个作用域来完成一些任务。
14+
15+
Kotlin则是Java的优化版,在解决Kotlin很多痛点的情况下,不引入过多的新概念。它具有强大的类型推断系统,使得语言有良好的动态性,其次是其语言招牌 —— 语法糖,Kotlin 的代码可以写的非常简洁。这使得 Kotlin 不仅做为常规编程语言能大放异彩,作为脚本语言也深受很多开发者喜爱。
16+
1317
它们共同特点就是基于JVM,可以和 Java 互操作。Gradle 能提供的东西, Kotlin 也能通过提供(闭包)。在功能上,两者能做的事情都是一样的。此外一些简单的差异有:
1418

15-
groovy 字符串可以使用单引号,而 kotlin 则必须为双引号
16-
groovy 在方法调用时可以省略扩号,而 kotlin 不可省略
17-
groovy 分配属性时可以省略 = 赋值运算符,而 kotlin 不可省略
19+
groovy 字符串可以使用单引号,而 kotlin 则必须为双引号
20+
groovy 在方法调用时可以省略扩号,而 kotlin 不可省略
21+
groovy 分配属性时可以省略 = 赋值运算符,而 kotlin 不可省略
1822
groovy 是动态语言,不用导包,而 kotlin 则需要。
1923

2024

2125

22-
为什么要用Kotlin DSL写gradle脚本
26+
为什么要用Kotlin DSL写gradle脚本?
27+
2328
撇开其他方面,就单从提高程序员生产效率方面就有很多优点:
2429

25-
脚本代码自动补全
26-
跳转查看源码
27-
动态显示注释
28-
支持重构(Refactoring)
30+
- 脚本代码自动补全
31+
- 跳转查看源码
32+
- 动态显示注释
33+
- 支持重构(Refactoring)
2934
3035
怎么样,要是你经历过groovy那令人蛋疼的体验,kotlin会让你爽的起飞,接下来让我们开始吧。
3136

3237
从Groovy到Kotlin
38+
3339
让我们使用Android Studio 新建一个Android项目,AS默认会为我们生成3个gradle脚本文件。
3440

35-
settings.gradle (属于 project)
36-
build.gradle (属于 project)
37-
build.gradle (属于 module)
41+
- settings.gradle (属于 project)
42+
- build.gradle (属于 project)
43+
- build.gradle (属于 module)
44+
3845
我们的目的就是转换这3个文件
3946

40-
第一步: 修改groovy语法到严格格式
47+
- 第一步: 修改groovy语法到严格格式
48+
4149
groovy既支持双引号""也支持单引号'',而kotlin只支持双引号,所以首先将所有的单引号改为双引号。
4250

4351
例如 include ':app' -> include ":app"
4452

4553
groovy方法调用可以不使用() 但是kotlin方法调用必须使用(),所以将所有方法调用改为()方式。
4654

47-
例如
55+
例如:
4856

57+
```java
4958
implementation "androidx.appcompat:appcompat:1.0.2"
5059
改为
5160

5261
implementation ("androidx.appcompat:appcompat:1.0.2")
5362
groovy 属性赋值可以不使用=,但是kotlin属性赋值需要使用=,所以将所有属性赋值添加=
63+
```
5464

55-
例如
56-
65+
例如:
66+
```
5767
applicationId "com.ss007.gradlewithkotlin"
5868
改为
5969
6070
applicationId = "com.ss007.gradlewithkotlin"
71+
```
72+
6173
完成以上几步,准备工作就完成了。
6274

6375

JavaKnowledge/HashMap实现原理分析.md

Lines changed: 19 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -49,10 +49,20 @@ HashMap是无序的,因为HashMap无法保证内部存储的键值对的有序
4949
获取对象时,我们将K传给get()方法,它调用hashCode()计算hash从而得到bucket位置,并进一步调用equals()方法确定键值对。
5050

5151
扩容前后,哈希桶的长度一定会是2的次方。这样在根据key的hash值寻找对应的哈希桶时,可以用位运算替代取余操作,更加高效。
52+
5253
而key的hash值,并不仅仅只是key对象的hashCode()方法的返回值,还会经过扰动函数的扰动,以使hash值更加均衡。
53-
因为hashCode()是int类型,取值范围是40多亿,只要哈希函数映射的比较均匀松散,碰撞几率是很小的。 但就算原本的hashCode()取的很好,每个key的hashCode()不同,但是由于HashMap的哈希桶的长度远比hash取值范围小,默认是16,所以当对hash值以桶的长度取余,以找到存放该key的桶的下标时,由于取余是通过与操作完成的,会忽略hash值的高位。因此只有hashCode()的低位参加运算,
54-
发生不同的hash值,但是得到的index相同的情况的几率会大大增加,这种情况称之为hash碰撞。即碰撞率会增大。
55-
扰动函数就是为了解决hash碰撞的。它会综合hash值高位和低位的特征,并存放在低位,因此在与运算时,相当于高低位一起参与了运算,以减少hash碰撞的概率。(在JDK8之前,扰动函数会扰动四次,JDK8简化了这个操作)扩容操作时,会new一个新的Node数组作为哈希桶,然后将原哈希表中的所有数据(Node节点)移动到新的哈希桶中,相当于对原哈希表中所有的数据重新做了一个put操作。所以性能消耗很大,可想而知,在哈希表的容量越大时,性能消耗越明显。扩容时,如果发生过哈希碰撞,节点数小于8个。则要根据链表上每个节点的哈希值,依次放入新哈希桶对应下标位置。因为扩容是容量翻倍,所以原链表上的每个节点,现在可能存放在原来的下标,即low位, 或者扩容后的下标,即high位。 high位= low位+原哈希桶容量如果追加节点后,链表数量 >=8,且只有数组长度大于64才处理,则转化为红黑树由迭代器的实现可以看出,遍历HashMap时,
54+
55+
因为hashCode()是int类型,取值范围是40多亿,只要哈希函数映射的比较均匀松散,碰撞几率是很小的。
56+
57+
但就算原本的hashCode()取的很好,每个key的hashCode()不同,但是由于HashMap的哈希桶的长度远比hash取值范围小,默认是16,所以当对hash值以桶的长度取余,以找到存放该key的桶的下标时,由于取余是通过与操作完成的,会忽略hash值的高位。
58+
59+
因此只有hashCode()的低位参加运算,发生不同的hash值,但是得到的index相同的情况的几率会大大增加,这种情况称之为hash碰撞。即碰撞率会增大。
60+
61+
扰动函数就是为了解决hash碰撞的。它会综合hash值高位和低位的特征,并存放在低位,因此在与运算时,相当于高低位一起参与了运算,以减少hash碰撞的概率。(在JDK8之前,扰动函数会扰动四次,JDK8简化了这个操作)扩容操作时,会new一个新的Node数组作为哈希桶,然后将原哈希表中的所有数据(Node节点)移动到新的哈希桶中,相当于对原哈希表中所有的数据重新做了一个put操作。所以性能消耗很大,可想而知,在哈希表的容量越大时,性能消耗越明显。
62+
63+
扩容时,如果发生过哈希碰撞,节点数小于8个。则要根据链表上每个节点的哈希值,依次放入新哈希桶对应下标位置。因为扩容是容量翻倍,所以原链表上的每个节点,现在可能存放在原来的下标,即low位, 或者扩容后的下标,即high位。
64+
65+
high位= low位+原哈希桶容量,如果追加节点后,链表数量>=8,且只有数组长度大于64才处理,则转化为红黑树由迭代器的实现可以看出,遍历HashMap时,
5666
顺序是按照哈希桶从低到高,链表从前往后,依次遍历的。
5767

5868
数组的特点:查询效率高,插入删除效率低。
@@ -70,7 +80,7 @@ HashMap在JDK1.8中发生了改变,下面的部分是基于JDK1.7的分析。H
7080
```java
7181
transient Entry[] table;
7282
```
73-
可以看到Map是通过数组的方式来储存Entry那Entry是神马呢?就是HashMap存储数据所用的类,它拥有的属性如下:
83+
可以看到Map是通过数组的方式来储存Entry,那Entry是神马呢?就是HashMap存储数据所用的类,它拥有的属性如下:
7484
```java
7585
static class Entry implements Map.Entry {
7686
final K key;
@@ -177,12 +187,11 @@ public V get(Object key) {
177187

178188
## JDK1.8
179189

180-
在Jdk1.8中HashMap的实现方式做了一些改变,但是基本思想还是没有变的,只是在一些地方做了优化,下面来看一下这些改变的地方,
181-
数据结构的存储由数组+链表的方式,变化为数组+链表+红黑树的存储方式,当链表长度超过阈值(8)时,且只有数组长度大于64才处理,将链表转换为红黑树。
182-
利用红黑树快速增删改查的特点来提高HashMap的性能,其中会用到红黑树的插入、删除、查找等算法。HashMap中,
183-
如果key经过hash算法得出的数组索引位置全部不相同,即Hash算法非常好,那样的话,getKey方法的时间复杂度就是O(1),
184-
如果Hash算法技术的结果碰撞非常多,假如Hash算法极其差,所有的Hash算法结果得出的索引位置一样,那样所有的键值对都集中到一个桶中,
185-
或者在一个链表中,或者在一个红黑树中,时间复杂度分别为O(n)和O(lgn)。
190+
在Jdk1.8中HashMap的实现方式做了一些改变,但是基本思想还是没有变的,只是在一些地方做了优化,下面来看一下这些改变的地方,数据结构的存储由数组+链表的方式,变化为数组+链表+红黑树的存储方式,当链表长度超过阈值(8)时,且只有数组长度大于64才处理,将链表转换为红黑树。
191+
192+
利用红黑树快速增删改查的特点来提高HashMap的性能,其中会用到红黑树的插入、删除、查找等算法。
193+
194+
HashMap中,如果key经过hash算法得出的数组索引位置全部不相同,即Hash算法非常好,那样的话,getKey方法的时间复杂度就是O(1),如果Hash算法技术的结果碰撞非常多,假如Hash算法极其差,所有的Hash算法结果得出的索引位置一样,那样所有的键值对都集中到一个桶中,或者在一个链表中,或者在一个红黑树中,时间复杂度分别为O(n)和O(lgn)。
186195

187196
![](https://raw.githubusercontent.com/CharonChui/Pictures/master/hashmap_data_structure.jpg)
188197

VideoDevelopment/OpenCV/1.OpenCV简介.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -127,7 +127,7 @@ copyTo()。
127127
在早期的OpenCV1.x 版本中,图像的处理是通过IplImage(该名称源于Intel 的另一个
128128
开源库Intel Image Processing Library ,缩写成IplImage)结构来实现的。
129129
130-
早期的OpenCV 是用C 语言编写,因此提供的借口也是C 语言接口,其源代码完全是C
130+
早期的OpenCV 是用C 语言编写,因此提供的接口也是C 语言接口,其源代码完全是C
131131
的编程风格。IplImage 结构是OpenCV 矩阵运算的基本数据结构。
132132
133133
到OpenCV2.x 版本,OpenCV 开源库引入了面向对象编程思想,大量源代码用C++重写。
Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
美颜滤镜
2+
---
3+
4+
美颜的基本原理就是深度学习加计算机图形学。
5+
6+
- 深度学习用来人脸检测和人脸关键点检测。
7+
- 计算机图形学用来磨皮、瘦脸和化妆容。
8+
- 一般在Android上使用OpenGL ES,iOS使用Metal。
9+
10+
## 美颜算法的原理
11+
12+
13+
美颜算法主要是基于图像处理技术,包括人脸检测、皮肤平滑、肤色调整、瘦脸大眼瞪。
14+
其中,人脸检测是美颜的第一步,通过算法识别出照片中的人脸区域,然后针对该区域进行后续的美化处理。
15+
16+
### 关键技术点
17+
18+
- 人脸检测:利用OpenCV(强大的计算机视觉库,支持人脸检测等)、Dlib等库实现。
19+
- 皮肤平滑:通过高斯模糊、双边滤波等技术减少皮肤瑕疵。
20+
- 肤色调整:调整肤色饱和度、亮度等,使肤色更加自然。
21+
- 瘦脸大眼:基于人脸关键点定位,通过变形算法实现。
22+
23+
24+
25+
### 人脸检测
26+
27+
- 人脸检测指的是对图片或者视频流中的人脸进行检测,并定位到图片中的人脸。
28+
- 人脸关键点检测是对人脸中五官和脸的轮廓进行关键点定位,一般情况下它紧接在人脸检测后。
29+
30+
31+
- 加载OpenCV库,在项目中集成OpenCV库,并加载本地人脸检测模型。
32+
- 实时处理:在相机预览的回调中,对每一帧图像进行人脸检测,并应用美颜算法。
33+
34+
35+
36+
37+
38+
https://zhuanlan.zhihu.com/p/163604590
39+
40+
41+
42+
43+
Lines changed: 74 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,74 @@
1+
2+
- 色温: 图片的色温指的是图片中呈现出来的整体颜色偏暖或偏冷的程度。
3+
4+
色温可以影响图像的分为和情感表达。简单理解就是色彩的温度,越低越冷如蓝色,越高越暖如红色。
5+
6+
- 色调: 色调是指图片色彩的整体质感,包括主要色调的选择和组合。
7+
8+
通过调整色调,可以改变图像的整体色彩效果,营造特定的视觉风格或情绪。简单理解就是色彩倾向,倾向于红橙还是黄绿。
9+
10+
- 亮度: 亮度描述了图片中各个部分的明暗程度。增加亮度将使整体图像看起来更明亮,减小亮度则会使图片变得更暗。
11+
12+
亮度的调整可以影响图像的整体视觉效果和光线感。
13+
增加就是给图片所有色彩增加白色,减少黑色。注意是只加黑白两种颜色,不然容易跟纯度弄混。
14+
15+
- 对比度: 对比度是描述图像中不同区域之间亮度差异的程度。
16+
17+
提高对比度会使图像中的明暗部分更加突出,增强图像的清晰度和视觉冲击力。
18+
适当的对比度可以让图像更具有立体感和层次感。
19+
增加就是让白的更白,黑的更黑。减少就是白的不那么白,黑的不那么黑。
20+
21+
- 饱和度: 饱和度表示图片中颜色的纯度和鲜艳程度。
22+
23+
增加饱和度会使颜色更加丰富饱满,减少饱和度会使颜色变得更加灰暗。
24+
调整饱和度可以改变图像的整体色彩和视觉吸引力。
25+
26+
简单理解就是增加图片各种颜色的纯度。
27+
比如蓝色,增加纯度就是在蓝色上加蓝色,降低纯度就是键入蓝色的对比色,让它变灰色或黑色。
28+
29+
- 高光: 高光是指图片中最亮的部分,通常实在光线照射下产生的明亮区域。
30+
31+
调整高光可以改变图像中亮部的强度和反射效果,从而影响图像的细节和光影效果。
32+
增加就是给图片白色的部分再加点白色,减少就是减少点白色。
33+
34+
35+
36+
37+
38+
### RGB颜色模型
39+
40+
RGB颜色模型是一种用于创建各种颜色的方法,它基于红色、绿色、蓝色三种颜色的组合。
41+
42+
通过调节这三种颜色的强度和比例,可以生成多种不同的颜色。
43+
44+
### HSV颜色模型
45+
46+
HSV代表色相(Hue)、饱和度(Saturation)、明度(Value),或色相(Hue)、饱和度(Saturation)、亮度(Brightness)。
47+
48+
在HSV模型中,色相同样表示颜色本身,饱和度表示颜色的纯度或浓淡程度,而明度或亮度则表示颜色的亮度程度。
49+
50+
HSV模型有时也被称为HSB(色相、饱和度、亮度)模型。
51+
52+
53+
HSV(HSB)颜色模型根据下图对应说明可以得知:
54+
55+
- H(Hue):色调,用角度度量,取值范围为0°~360° ,从红色开始按逆时针方向计算
56+
- S(Saturation):饱和度,表示颜色接近光谱色的程度.一种颜色,可以看成是某种光谱色不白色混合的结果.通常取值范围为0%~100%,值越大,颜色越饱和.光谱色的白光成分为0,饱和度达到最高.
57+
- V(Value或Brightness):明度,表示颜色明亮的程度.
58+
59+
60+
61+
### HSL颜色模型
62+
63+
HSL代表色相(Hue)、饱和度(Stauration)、亮度(Lightness)。
64+
65+
在HSL模型中,色相表示颜色本身,饱和度表示颜色纯度或浓淡程度,亮度则表示颜色的明暗程度。
66+
67+
- H: 色相,使用不水平轴之间的角度来表示,范围是从(0 ~ 360)度。从蓝色开始。
68+
- S: 饱和度,说明颜色的相对浓度。
69+
- L: 亮度,在L=0处为黑色,在L=1处为白色。灰色沿着L轴分布。
70+
71+
72+
73+
74+

0 commit comments

Comments
 (0)