重构:改善既有代码的设计
基于 Refactoring: Improving the Design of Existing Code, Second Edition 编写
重构的原则
注意,重构应该是一小步一小步进行的,每一步都不应该破坏代码的功能。因此,最为理想的重构流程应当是修改-测试-提交并一步步迭代。
重构的目标是让代码更加模块化,或者探究其本质,是让代码能够被人读懂。正如作者所说:
Any fool can write code that a computer can understand. Good programmers write code that humans can understand.
任何傻瓜都会写出能够让机器理解的代码,只有好的程序员才能写出人类可以理解的代码。
添加新功能和重构应该是两个不同的过程,通常是在添加新功能之前,发现现有的的代码结构无法较好地添加新功能,所以先重构。两个过程应当是交替进行的,而不是同时进行
为什么要重构?
提高软件的设计
使软件更容易被理解
帮助寻找 bug
从长期来看,能提高编程的速度
重构类型:
准备重构:使添加新特性更容易
理解重构:使代 ...
Docker
安装与配置
Docker 有利于更轻松的部署,更一致的运行环境,同时相比传统的虚拟机,开销更小
基本概念:镜像 image、容器 container、仓库 repository
从仓库获取镜像,从镜像启动容器
国内镜像源:
阿里云加速器(点击管理控制台 -> 登录账号(淘宝账号) -> 右侧镜像工具 -> 镜像加速器 -> 复制加速器地址)
网易云加速器 https://hub-mirror.c.163.com
百度云加速器 https://mirror.baidubce.com
Docker 也有 hello world:
docker pull hello-worlddocker run hello-world
镜像
Docker Hub 上有大量镜像,获取的方法是:
docker pull 仓库名[:标签]
docker image ls 列出镜像,docker image rm 镜像名或 ID 删除镜像
Dockerfile 定制镜像
构建方法:
docker build -t 目标镜像名 上下文路径
常见指令:
FROM 指定镜像
RUN 执行指 ...
CMake
运行 CMake
现代 CMake 可以直接在根目录下执行指令了,而不是要进入 build 目录:
cmake -B buildcmake --build build
如果想要安装,也只需要一行命令:
cmake --install build
手动指定编译器:
CC=clang CXX=clang++ cmake ..
可以使用 -G"My Tool" 来选择自己想要用的构建工具(GNU Make,MSBuild 等)
基础介绍
CMakeLists.txt 中的第一行指明 CMake 的版本:
cmake_minimum_required(VERSION 3.7...3.29)if(${CMAKE_VERSION} VERSION_LESS 3.12) cmake_policy(VERSION ${CMAKE_MAJOR_VERSION}.${CMAKE_MINOR_VERSION})endif()
设置项目:
project(MyProject VERSION 1.0 ...
Test
Benchmark
JMH
jmh(Java Microbenchmark Harness) 是 Java 微基准测试框架,可以用于比较 Java 程序的性能好坏
万物皆可 hello world:
package org.openjdk.jmh.samples;import org.openjdk.jmh.annotations.Benchmark;import org.openjdk.jmh.runner.Runner;import org.openjdk.jmh.runner.RunnerException;import org.openjdk.jmh.runner.options.Options;import org.openjdk.jmh.runner.options.OptionsBuilder;public class JMHSample_01_HelloWorld { @Benchmark public void wellHelloThere() { } public static void ...
C++ Concurrency In Action
基于 C++ Concurrency In Action Second Edition 编写
C++ 并发世界
并发 concurrency 是指两件或更多分开的活动在同时发生
单核 CPU 通过 context switch 来形成多个任务在同时执行的假象
多核 CPU 原理也类似
并发的方法:
多进程
多线程
并发和并行 parallelism 概念类似,但是
并行通常更考虑效率
并发则关心关注点分离
故使用并发的情况:
关注点分离
任务和数据的并行
C++ 中原来没有关于并发的标准,和 C 语言一样使用操作系统提供的 API。从 C++11 开始,封装了较一般的 thread 等
从并发版的 hello world 开始:
#include <iostream>#include <thread>void hello() { std::cout << "Hello, World" << std::endl;}int main() { std::thread t( ...
Butterfly 博客魔改
音乐
这里直接采用 html 的格式
<div class="aplayer" data-id="760533" data-server="netease" data-type="song"></div>
效果:
参数解释:
选项
description
data-id
song id / playlist id / album id / search keyword
data-server
音乐平台:netease、tencent、kugou、xiami、baidu
data-type
song、playlist、album、search、artist
关闭 asset_inject:
_config.ymlaplayer: meting: true asset_inject: false
开启主题的 aplayerInject:
_config.butterfly.yml# Inject the css and script (aplayer/m ...
Hexo 和 Butterfly 搭建博客
Hexo 是基于 Nodejs 开发的博客框架,简单,扩展性强。尽管性能不是很强,但对于轻量使用博客来说已经足够了
第一个 Hexo 博客
安装 Hexo:npm install -g hexo-cli
初始化项目名:hexo init 项目名
生成的项目结构如下:
文件夹名
说明
node_modules
依赖包
scaffolds
生成文章的模板
source
用来存放你的文章
themes
主题
.npmignore
发布时忽略的文件
_config.landscape.yml
主题的配置文件
_config.yml
博客的配置文件
package.json
项目名称、描述、版本、运行和开发等信息
启动项目:hexo s
在 http://localhost:4000/ 中可以看到页面
这里使用 GitHub Pages 部署博客,按照说明新建用户仓库
安装 hexo-deployer-git:npm install hexo-deployer-git
修改文件:
_config.yml# Deployment## Docs: ht ...
UML
基于 UML Distilled Third Edition: A Brief Guide to the Standard Object Modeling Language 编写
在线画图网站:draw.io
简介
统一建模语言 Unified Modeling Language(UML) 是图像标记家族,通常用于面向对象编程中
标准由 OMG 制定
UML 通常有三种用法:
草稿——最常用
蓝图
编程语言
两个时间阶段:
前向工程:在写代码之前画图
逆向工程:从现有的代码中构造 UML 图以帮助理解代码
也正因为前两种用法更常见,故应该力求简洁,抓住要点,就像设计模式一样,通过公认的规范让人能够快速抓住要点。所以在使用的过程中要尽量避免那些微妙的歧义之处
类图
类图是最常见的图之一
属性 properties 代表类的结构化特征,有两种标记方式:
Attribute:直接写在类的框图中
通常语法如下:可见性 名字: 类型 乘数 = 默认值 {属性字符串}
例如:- title: String [1] = "Untitled" ...
WSL2
邪教——适用于 Linux 的 Windows 子系统(WSL2)
尽管 WSL2 中的 Linux 内核是不完整的,但几乎已经足够使用了。而且其无论是启动速度还是易用性方面都比虚拟机好得多,而且 IP 地址相同
参考文档:适用于 Linux 的 Windows 子系统文档 | Microsoft Learn
安装
wsl --install
查看可用非发行版:wsl --list --online
列出已安装的版本:wsl --list --verbose
安装指定 Linux 发行版:wsl --install -d <distribution name>
运行指定 Linux 发行版:wsl --distribution <Distribution Name>
设置默认 Linux 发行版:wsl --set-default <Distribution Name>
关闭:wsl --shutdown
设置开发环境
换源:使用中科大源
这里使用的是最新的 Ubuntu 24.04,使用其提供的命令:
sudo sed -i 's@//. ...
Effective Modern C++
基于 Effective C++: 42 Specific Ways to Improve Your Use of C++11 and C++14 编写
推断类型
理解模板类型推断
在模板类型推导中,引用参数被视为非引用
对通用引用 && 参数,左值参数特别对待
在按值传递参数时,const 和 volatile 参数被视为非 const 和非 volatile
在模板类型推导中,数组或函数名参数退化为指针,除非被用于初始化引用
理解 auto 类型推断
auto 通常和模板类型推断一样,但是 auto 类型推断将大括号初始化 {} 视为 std::initializer_list,模板类型推断不这样
函数返回值中的 auto 或 lambda 参数是函数模板推断,不是 auto 类型推断
理解 decltype
decltype 在没有任何修改的情况下,几乎总是生成变量或表达式的正确类型
对于不同于名字的类型为 T 的左值表达式,decltype 总是返回 T&
decltype(auto) 类似于 auto,从初始化推断类型,但是使用了 ...