将VSCode或NVim作为C++的开发工具

简介 最近C++代码越写越多,也有不少同学问我这种炫酷的C++代码提示是怎么在Mac上实现的。我自己日常会使用NVim来作为主力编辑器,而使用VSCode来进行断点调试和提交Git Commits。我会以MacOS系统为例配置这两种方案,大家根据自己需求,选择其中一种即可(推荐VSCode) Sec. 1 VSCode 首先是要安装 C/C++ 拓展,启动VSCode以后在拓展里搜索安装即可。然后让我们找个(或者新建)一个空的文件夹,例如我选择了 ~/Code/clang/playground,使用VSCode打开它。接着新建 .vscode 文件夹,在该文件夹下新建文件 c_cpp_properties.json 文件: { "configurations": [ { "name": "Mac", "includePath": [ "${default}", "${workspaceFolder}" "/usr/local/opt/root/include/root", ], "compilerPath": "/usr/bin/g++", "cppStandard": "gnu++17", "intelliSenseMode": "gcc-x64" } ], "version": 4 } 所有你需要进行智能提示的库,你都要写到 “includePath” 中,例如在上面的例子我添加了root库的inlude路径。另外你可能需要更改 “compilerPath” ,你可以在终端里输入 which g++ 来看到g++的路径。然后让我们来测试一下它是否能够工作,新建一个 main.cc 文件,如下: #include <TFile.h>#include <TCanvas.h>#include <TGraph.h>#include <TAxis.h> int main() { int n = 20; // create canvas and graph auto c1 = new TCanvas("c1","A Simple Graph Example",200,10,700,500); auto gr = new TGraph(n); // set mock sin data for(int i=0; i<n ;i++) gr->SetPoint(i, i*0....

April 28, 2021 · 3 min · Bruce Yip

SSH使用技巧-免密码/自动代理

Sec.0 引言 如果你刚接触GNU/Linux,那么在连接远端主机的时候一定被这些问题困扰着: 远端主机的IP地址记不住,每次都要掏出小本子看一下,还要多看几眼看看输地对不对 密码过长难以输对,或者密码太过简单容易被碰撞攻击 连接的网络环境复杂,每次要跳转多个堡垒机到达目标 不过幸好,前辈们在设计SSH的时候,就已经帮我们考虑到了这个问题。 Sec.1 通过密钥来避免每次输入密码 什么是非对称加密算法 你生成了两把钥匙:“公共钥匙”和“私人钥匙”。公钥会被广泛地分发给其他任何想要和你通信的人;而私钥则由你自己保管。 “钥匙对”使得通信过程中,不需要传递加密解密“规则” 你把公钥给了信任的人,他们将要发送的数据通过公钥加密 你拿到了这段数据,利用只储存在自己这里的私钥解密 中间数据即使被拦截,在没有唯一私钥的情况下,也没法解开数据包。 那么只要私钥不泄漏,通信就是安全的。 在数学原理上,阮一峰的博文RSA算法原理(一)做了很好的阐述,这里不再展开,有兴趣的同学可以了解一下。 生成钥匙对 # 生成key,但首先你得安装ssh ssh-keygen -t rsa -b 2048 # 一路按回车换行,终端输出大概是这样 # Generating public/private rsa key pair. # Enter file in which to save the key (/home/username/.ssh/id_rsa): # Enter passphrase (empty for no passphrase): # Enter same passphrase again: # Your identification has been saved in /home/username/....

October 16, 2020 · 1 min · Bruce Yip

如何在两周内学会C++并构建优质的项目

简介 最近因为科研需要,捡起了好几年前大学水平的C++(不忍直视),毫无意外地忘记地一干二净。于是两周后就有了这篇文章,期望能够帮助所有拥有一定编程基础(至少写过一个完整的项目的那种)的同学入门并掌握这一门编程语言。通过阅读这篇文章,你能够学到: 用优质的资源,快速学习C++的语法构成 指针和防止内存泄漏等,较难的需要实战(编码)的内容 C++标准的现代化目录结构 利用CMake来进行跨平台开发/编译,把开发的软件安装到系统中 利用Catch2来编写单元测试,集成到CMake中去 Doxygen自动化生成API文档 Shell脚本与CMake联动,进一步实现自动化(龟速更新中) 跨系统交叉编译,做成Docker镜像(未来用到了再更) 我的开发平台是"macOS Catalina",选择的IDE是"vscode",编译器采用了"g++",在考虑兼容性和新特性之后,我选择了"c++17"版本进行开发。文中许多的资源,是需要梯子才能够访问的,这点请注意。 快速学习C++语法结构 写出你的 “Hello, world!"(VSCODE配置) 首先,让我们从简单难度开始:在你的本地代码仓库中建立一个文件夹,名字随意,创建一个 hello.cc 文件并保存,内容如下(现在不需要去关心这些内容代表什么): #include <iostream> int main() { std::cout << "hello, world!" << std::endl; return 0; } 打开 terminal 以后,你就可以进行手动编译了: # 编译 g++ hello.cc -o hello.o # 运行 ./hello.o 当然,每次进行这样的手动编译,实在繁琐并且无法进行断点调试。在VSCODE中编写C++项目,首先你要安装一个"C/C++“的扩展,然后打开刚才存放 hello.cc 的目录,双击打开 hello.cc 以后,按住 cmd+shift+p 呼出vscode的命令面板,输入 tasks: 索引到 “Tasks: Configure Task”(如图所示)选择编译器,这里我选择了g++作为编译器,之后你能在.vscode目录下发现自动创建出的 “tasks.json”(当然我们要进行修改) 之后选择左侧的调试按钮,创建一个 “launch.json”,附上我的两个配置文件如下: .vscode/task.json { "version": "2.0.0", "tasks": [ { "type": "shell", "label": "C/C++: g++ build active file", "command": "/usr/bin/g++", "args": [ "-std=c++17", "-g", "${file}", "-o", "${fileDirname}/caches/${fileBasenameNoExtension}....

September 20, 2020 · 5 min · Bruce Yip

博客搭建指南(零):基础知识及架构

简介 近期有不少同学提到我写的这个系列写的看不太懂(捂脸.jpg),大概是我没有介绍清楚自己的架构和思路。那么,这篇文章能带给你: 博客和个人服务器的整体架构 域名和现代网页的一些基本常识 服务器和操作系统的选择 注:文章更多的是一些原理和为什么(WHY-TO)我相信你有了这些相关的关键词以后,能够通过搜索引擎找到具体的操作(HOW-TO) 架构及原理 云服务器是什么 首先很容易混淆的概念就是,物理服务器与网页伺服器(大白话) 前者就是一台在远端的带操作系统的电脑,而后者则是在这台电脑上一直跑着的一个软件。 网页伺服器负责接收所有指向到这台电脑的HTTP请求,然后进行处理,返回相应的网页给请求者。从这种意义上来说,你也可以在你的个人电脑上安装一个网页伺服器(例如,Apache,Nginx,IIS,Caddy,等等),然后让你室友来请求你的IP地址,你就可以返回一个标准的网页给TA了。 然而,你的个人电脑不可能保持24小时开机的状态,所以这个时候我们就需要一些商业公司(例如,AWS,Azure,Google Cloud,阿里云,等等)提供的云服务器,我们不再需要关心这台“云电脑”是否会坏,它也能保持一直开机的状态。 现代的云服务器一般都是按小时制来进行结算的,有些提供商也会有包月的套餐选项(包月包年的都是耍流氓,说的就是你,阿里云)。对于我们的需求,一台单核心、1G可运行内存、10G的普通硬盘,就能完全满足了(甚至不如一台老年手机的配置)。 我们需要购买一台云服务器,还要选择一个网页伺服器软件。 关于代理 这是一个相对敏感的话题,所以我只略微提几句。-G-F-W-(不懂就搜索一下)是一个黑盒子,看不到它的代码,我们只能凭借许多人的经历去猜测它的审查机制。 那么为什么我们还能够绕过它呢?因为现代互联网是相对安全的,只要你使用的技术得当,没人能够拆开你的数据包看你到底给接收者发送了什么内容。 可是为什么-G-F-W-还能对各种代理服务器进行封禁操作?因为它钻了现代互联网设计的空子,举个例子:你发送给代理服务器的内容,都是指向到它某个固定的端口(非80,非443)并且它的主端口(80,443)是访问不到任何内容的,再并且它与你的通信数据类型都是非常单一的,那么,你说这台服务器是不是良民?显然不是,-G-F-W-会对你的数据包进行嗅探,会分析你目标服务器的特征,等等。 国家级的安全设施,不是在开玩笑。 国内可以使用的主流手段,从-S-S-演化到-S-S-R-,再到-S-S-R-作者被请去国安局喝茶,最后到现在的-V-2-R-A-Y-,俨然是一部超长的宫斗剧了。前两者早就不好使了,我从2018年开始使用最后者,到现在也没有被封禁过任何一台服务器。你需要记住的是: 无论未来宫斗剧怎么演变,合理的架构设计大于任何混淆协议,因为现代互联网技术,是相对安全的。 域名 你有没有思考过这个问题:当我访问 https://bing.com 的时候,它怎么知道我发起的请求,到底被哪一台真实的物理服务器(电脑)处理并给了我网页呢? 一台真实的物理服务器,它会有自己唯一的一个的全球IP地址(例如:45.77.5.214),这样,我在全球任何一个位置,向这个地址发送消息,都可以定位到这台电脑。所以,你必须要一个第三者,相当于电话号码本,把bing.com查找变成45.77.5.214(这么设计的原因是抽象的数字人们记不住) 我们称bing.com为域名(domain),45.77.5.214为公共的IP地址(public ip address),第三者为DNS服务器(负责把域名翻译成公共IP的)。 那么思路就非常简单了:当你在浏览器里键入bing.com并按下回车键,请求开始,先通过UDP协议向DNS服务器发送请求获得域名的真实IP地址,接着真正的请求通过TCP协议向这个IP地址发送数据包,远端服务器处理好你的数据包,将网页内容再通过原管道塞回给你。 有一些很皮的同学就要问了,那为什么我们在纯粹搭建代理的时候,不能够抛弃域名通过IP地址+443端口的方式来做呢?不行!这个和我们的整体架构有关,先说结论,因为开启HTTPS加密必须需要一张证书,而证书需要用域名来申请! 域名诞生之初,是为了人们能够记住你的网站,而之后域名也被划入了安全性考虑。 架构设计 网页伺服器软件选用的是 Caddy v2,代理选用的是-V-2-R-A-Y-(可能被墙掉了),我们购买了域名通过配置Caddy来自动获取HTTPS证书,以获取TLS加密(例如你打开bing.com,chrome浏览器能看到地址栏最左边有一把锁,说明你很安全)。代理则使用Websocket协议+TLS加密来使它看起来和一般的HTTPS流量特征一致。到达网页伺服器的代理流量,则会被根据请求路径分发到-V-2-R-A-Y-中,由它处理。 上面那一大段出现了一些术语,这里再做一些科普。早期的HTTP协议是无状态的,并且传输时是非加密的,也就是说可能请求会在流到网页伺服器之前就被截获,破译你的消息。想象一下你使用咖啡店里的公共WIFI,在登陆某个网页时被咖啡店里的处于同一网段的某个黑客截获了,那真是太不幸了。 后来设计者们发现这太蠢了,于是就在传输层加入了额外的保障:TLS,它能够保证建立连接的双方是加密通信,并且能够保证信息的完整性。我们现在提到的HTTPS,其实就是 HTTP+TLS 的传输设计,即便你的消息被第三方截获,他也没法进行反向解密(解密需要私钥,而私钥则存在接收者的电脑中)。 另一个HTTP协议的缺点,也来自于它的无状态特性(因为起初的设计是这样:网页伺服器不需要知道到底是谁来请求我,我只要把你请求的内容给你就完了),它把某个文件传输给你以后,就停止工作了,等待下一个请求。所以HTTP协议没法进行状态保持,也就是网页伺服器只能被动接受请求,而没法主动向某个电脑发送一段消息(如果可以的话那简直就是场灾难,黑客可以随意向你发送消息)所以在互联网早期,双向通信的实现非常费劲。 Websocket协议(同理还有类似的HTTP1.1版本中的长连接特性,但我们说不好未来到底是谁获胜)则刚好完美地弥补了这个缺点,你能和代理服务器建立长时间的连接(而不是发完一段数据包就断开了),你和代理服务器的消息能进行双向推送,这不正是我们想要的吗? 这样,我们设计的整个系统,所有数据包(无论是静态网页,还是代理)都是通过HTTPS协议(443端口)流到云服务器的。我们是良民中的良民,因为从头至尾表现的都是一个正常的网站啊! 注:中国移动用户请留意,内部还有一个局域网+防火墙,我没研究过怎么穿越它,请更换联通/电信。 域名与服务器购买 推荐 Google Domain 来购买域名,Google Cloud Platform 来购买服务器,不接受反驳。 理想很丰满,但现实是你一开始如果没有梯子,根本使用不了Google的所有服务,这个时候只能退而求其次,使用 Godaddy + Vultr 这对能用支付宝付款的组合了,但相对来说体验就不是很好。尤其是Vultr机房的整个IP区段(ipv4 + ipv6)全部被 Google Scholar 封杀了,一点办法都没有,这对于做科研的我们并不是一个好消息。 购买了域名以后,你还需要配置域名解析,把它指向到你购买的服务器(公共IP地址),这些网上都有很多教程,不再赘述,实在有问题你可以发邮件给我。 这里再补充一句,Google Cloud 的 us-west(oregon) 节点,其 f1-micro 配置是永久免费的,虽然其配置较低(单核心,614MB内存,10G普通硬盘)但也足够使用,我在上面跑了一个博客+代理+Docker搭建的几个动态应用,也运行良好。这意味着你只需要出流量费就可以了,流向境内的是0....

July 1, 2020 · 1 min · Bruce Yip

从泰坦尼克号谈到浅层神经网络

前言 最近因为课题需要,捡起了很多年前学了但是没怎么应用的机器学习。作为一个经典的算法,逻辑回归目前被作为神经网络诞生前的基础,具有广泛的应用。单层单节点的逻辑回归在“泰坦尼克号生还概率预测”这个问题上表现较为良好(~78%准确度)。本文的在线示例是用大约600条历史上泰坦尼克号上的搭乘者->生还/死亡数据,喂给一个3层的神经网络训练而成。对于以下细节,你或许会感兴趣: 数据集:训练样本627条,测试样本264条 准确度:训练集88%,测试集83%,尚未进行超参数优化(还没来得及做) 模型状况:三层的浅层神经网络,节点数分别为:128(ReLU), 64(ReLU), 1(Sigmoid) 源码:qwezarty/machine-learning-examples 注:在线演示的参数验证并不严格,还请大家手下留情不要用表单工具提交一些奇怪的值(要是把AI玩坏了,她会来找你算账的),另外为了简化输入,我使用下拉选项替代了许多的文本框。好了,现在大家就可以由观看《泰坦尼克号》的经验,有序上船,会不会翻全看造化啦! 在线示例 性别(只接受男/女噢): 男 女 年龄(5-80之间都很合理): 20 21 22 23 24 25 26 27 28 29 30 35 40 45 50 60 70 80 5 10 15 船票等级: 三等舱 一等舱 二等舱 船票费用: 0(偷渡的或工作人员) 5 10 15 30 35 40 50 100 200 船舱位置: 我也不清楚 C G A B D F E 登船港口: 南安普敦, Southampton 瑟堡, Cherbourg 皇后镇,Queenstown 我也不清楚 是否单独一人: 否 是 登船的配偶及亲兄弟/姐妹人数: 1 2 3 4 0 登船的父母/子女人数: 0 1 2 3 5 来吧,决定命运的时候到了! 本AI认为你大约有%的几率生还。 document....

June 4, 2020 · 1 min · Bruce Yip