## javaparser
### 使用Java Parser转换生成AST
Java Parser转换生成AST,有很多方法,主要支持两大类方式:
**1) 输入为文件**
输入为文件,即针对完整的文件为输入,生成整个文件的AST(对于Java来说,如果是整个Java文件,AST的根节点为CompilationUnit),这种方式,可以完整保留源码的代码行信息,这样方便进行分析。对于文件为输入,即输入文件路径(多种写法,例如String、File、Path、Resource等,其实都是表示文件路径),同时可以指定文件的编码方式,下面的用例,指定的是nio的Path格式的路径。
~~~javascript
// 1. 转换的是完整的Java文件
File base = new File("");
String relativePath = "test-case/javaparser-testcase/src/main/java/zmj/test/thread/MyThread.java";
String absolutePath = base.getCanonicalPath() + File.separator + relativePath;
ParseResult<CompilationUnit> result = new JavaParser().parse(Paths.get(absolutePath));
result.getResult().ifPresent(YamlPrinter::print);
~~~
### AST
![](https://img.kancloud.cn/76/45/7645e5cefe463e6653b6372b3a8f3769_708x758.png)
![](https://img.kancloud.cn/8e/67/8e6725c9abd633b5761d10f0b4d9c91e_1197x347.png)
### 应用
#### 源码间依赖关系分析
基于类型推断获取如下信息:
1) 当前类的父类或者父接口,并递归获取所有的父类和父接口;
2) 获取当前所调用函数的signature(函数签名,包含可以唯一识别一个方法的所有信息,例如所在的类、名字、形参类型列表、返回值类型),从而拿到函数调用关系;
另外,再结合源码文件和Java类定义的对应关系,可以很方便地构造出工程的CG图,识别出源码之间的依赖关系分析。
#### 代码度量
实际上,基于Java Parser获得的AST信息,辅助类型推断特性,可以实现针对源代码的各种度量内容。可以参考[https://www.exida.com/Blog/software-metrics-iso-26262-iec-61508](https://www.exida.com/Blog/software-metrics-iso-26262-iec-61508), 查看常见的代码度量项。针对其中3.1所列出的所有的项都可以度量。
常见的一些度量项:
针对函数:圈复杂度、代码深度、各类代码行信息、调用函数数量、被调用次数、其他诸如入参个数…;
针对文件:总代码行、空行、注释行、非空非注释行、代码注释密度…;
针对工程:文件总数、代码行总数、平均代码行…
基于Java Parser可以很好地进行实现,而且大部分都不需要完整的依赖信息,可以方便地进行度量。
#### Java规范支持检查
当前,针对各类规范支持,可以在不同的层面上进行支持,例如直接对源码检查、对解析得到的Token进行检查、对AST进行检查、在CFG和CG上进行数据流检查和各种形式化检查等。
基于Java Parser,可以实现在AST及源码(可以直接读取源码信息)、Token(从AST的节点可以获取当前AST Node中的所有的Token)相结合的所有检查。
例如,PMD主要是在AST上进行的检查,CheckStyle主要是在Token和AST上进行的检查,结合类型推断的支持,Java Parser可以实现比PMD和CheckStyle更精确的检查。
# 参考资料
[Java Parser应用介绍](https://cloud.tencent.com/developer/news/740798)
- Android
- 四大组件
- Activity
- Fragment
- Service
- 序列化
- Handler
- Hander介绍
- MessageQueue详细
- 启动流程
- 系统启动流程
- 应用启动流程
- Activity启动流程
- View
- view绘制
- view事件传递
- choreographer
- LayoutInflater
- UI渲染概念
- Binder
- Binder原理
- Binder最大数据
- Binder小结
- Android组件
- ListView原理
- RecyclerView原理
- SharePreferences
- AsyncTask
- Sqlite
- SQLCipher加密
- 迁移与修复
- Sqlite内核
- Sqlite优化v2
- sqlite索引
- sqlite之wal
- sqlite之锁机制
- 网络
- 基础
- TCP
- HTTP
- HTTP1.1
- HTTP2.0
- HTTPS
- HTTP3.0
- HTTP进化图
- HTTP小结
- 实践
- 网络优化
- Json
- ProtoBuffer
- 断点续传
- 性能
- 卡顿
- 卡顿监控
- ANR
- ANR监控
- 内存
- 内存问题与优化
- 图片内存优化
- 线下内存监控
- 线上内存监控
- 启动优化
- 死锁监控
- 崩溃监控
- 包体积优化
- UI渲染优化
- UI常规优化
- I/O监控
- 电量监控
- 第三方框架
- 网络框架
- Volley
- Okhttp
- 网络框架n问
- OkHttp原理N问
- 设计模式
- EventBus
- Rxjava
- 图片
- ImageWoker
- Gilde的优化
- APT
- 依赖注入
- APT
- ARouter
- ButterKnife
- MMKV
- Jetpack
- 协程
- MVI
- Startup
- DataBinder
- 黑科技
- hook
- 运行期Java-hook技术
- 编译期hook
- ASM
- Transform增量编译
- 运行期Native-hook技术
- 热修复
- 插件化
- AAB
- Shadow
- 虚拟机
- 其他
- UI自动化
- JavaParser
- Android Line
- 编译
- 疑难杂症
- Android11滑动异常
- 方案
- 工业化
- 模块化
- 隐私合规
- 动态化
- 项目管理
- 业务启动优化
- 业务架构设计
- 性能优化case
- 性能优化-排查思路
- 性能优化-现有方案
- 登录
- 搜索
- C++
- NDK入门
- 跨平台
- H5
- Flutter
- Flutter 性能优化
- 数据跨平台