C# 实现自定义"应用程序设置"的配置文件(user.config)存储路径

关于“应用程序设置”: 前往MSDN查看

默认提供的 SettingsProvider 不允许我们修改应用程序设置的配置文件的路径,这就导致了以下问题:

  1. 设置保存在了 %appdata% 目录下,使应用程序不够绿色化
  2. 当用户把程序拷贝到其他电脑上时,设置将丢失
  3. 当用户升级程序时,设置将丢失(自带的 Upgrade() 过于复杂)

要解决上述问题,就需要由我们自己来定义在哪里存储应用程序设置
MSDN给出的方法是:自己实现一个 SettingsProvider

Win10 资源管理器为所有格式激活“编辑”按钮并修改文本文件“编辑”按钮的编辑器

默认情况下,Windows 10 资源管理器的功能区对绝大多数文本格式的不可用的,即使能够使用(例如 .js .cpp .txt 等格式),“编辑”按钮所对应的编辑器也是废物一般的记事本(用记事本写代码?),使得这个“编辑”按钮显得华而不实。为了让编辑文本更加方便、充分利用这个“编辑”按钮,本文将介绍如何通过修改注册表以为为所有格式激活“编辑”按钮并修改文本文件“编辑”按钮的编辑器

思路

Windows10 功能区的“编辑”按钮可用与否取决于注册表中HKEY_CLASSES_ROOT中对应的格式下的shell项是否存在edit子项,若edit项存在,则该按钮可用
只需增加edit子项并设置启动命令行即可激活编辑按钮或达到更改编辑器的目的

实现

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
Windows Registry Editor Version 5.00

[HKEY_CLASSES_ROOT\*\shell]

[HKEY_CLASSES_ROOT\*\shell\edit]

[HKEY_CLASSES_ROOT\*\shell\edit\command]
@="\"编辑器路径\" \"%1\""

[HKEY_CLASSES_ROOT\txtfile\shell]

[HKEY_CLASSES_ROOT\txtfile\shell\edit]

[HKEY_CLASSES_ROOT\txtfile\shell\edit\command]
@="\"编辑器路径\" \"%1\""

将上述代码中的 编辑器路径 替换为你的编辑器的路径,然后将上述代码保存为 1.reg ,双击导入即可

留言板

这是一个留言板,它什么都不做 #(滑稽)

又一次 Hello world

是的我又回来了蛤铪蛤铪蛤铪蛤铪蛤铪

(假装笑得很开心)

Java 学习笔记 (仍在更新)

Java 学习笔记 #3

by kenvix @ 2018-11-10 pm

概念这种东西就是应付考试,实际生产中懂概念的不如有经验的。

多态

概念: 相同类型的变量、调用同一个方法时呈现出多种不同的行为特征,称为多态。

Java 中的多态与 TypeScript, C# 中的多态

这三种语言的处理策略不同,涉猎语言较多的用户可能会因此写出 Bug。

Upcasting in C

考虑代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
class Father
{
public void Test()
{
Console.WriteLine("father");
}
}
class Child : Father
{
public void Test() //equals: public new void Test()
{
Console.WriteLine("child");
}
}

class Program
{
static void Main(string[] args)
{
Father father = new Child();
father.Test();
}
}

输出:father

Upcasting in java

考虑代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24

class Sunzi extends Test {
public void child() {
System.out.println("child!");
}

@Override
public void nmbd() {
System.out.println("extend!sunzi");
}
}

public class Test {
public void nmbd() {
System.out.println("super!");
}

public void father() {
System.out.println("father!");
}
}

Test test = (Test)new Sunzi();
test.nmbd();

输出:extend!sunzi

Java 中,test 的 运行时类型是 Sunzi 而不是 Test,这就导致其方法特征始终呈现为子类的特征,即实际调用了子类的方法
而在编译其则呈现父类特征,即你不能调用 test.child();

Note: 实例变量与 C# 相同,均为父类的实例变量。

Upcasting in TypeScript

考虑以下 TypeScript 代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
class father {
public test() {
console.log("father");
}
}

class child extends father{
public test() {
console.log("child");
}
}

const f: father = new child();
f.test();

输出:child
TypeScript 最终是要类型擦除输出JavaScript的,这种类型注解没有任何意义。

拆装箱

即对 基本数据类型 和 包装类型 的直接赋值操作,等效过时的new, getValue。

++ Object 是它们的子类,因此有这种智障操作:

1
2
Object obj = 666; //自动 upcasting
int i = (Integer)obj; //用作编译期

许多智障面试官也许会出这种问题

1
2
3
4
5
6
7
8
Integer a = 1;
Integer b = 1;
a == b // true
b = 199;
a == b //false (unlinked)
Integer c = 666;
Integer d = 666;
c == d //false

Java 对 -128~127 的 Integer 进行了缓存,故 a b 指向同一个数据。

立刻转 C# 保平安。

字符串常量池

1
2
3
4
5
6
7
String str1 = new String("fuck");
String str2 = new String("fuck");
String str3 = "fuck";
String str4 = "fuck";
System.out.println(str1==str2); //false
System.out.println(str1==str3); //false
System.out.println(str4==str3); //true

直接使用 String x = “” 表达式赋值的字符串由 JVM 常量池直接接管,相同的字符串引用将指向池中相同的值。
而 String str1 = new String(“fuck”); 则创建了字符串对象到 heap。

IDEA 明确告诉你这种方法很垃圾,但是sb面试官还是要问。

Java 学习笔记 #2

by kenvix @ 2018-11-07 am

java学得越深,越发觉得kotlin香

数据类型

参数传递

java 仅有值传递。传递一个对象时,传递该引用该对象的变量的拷贝(stack中产生引用变量的副本),但引用相同的对象,heap没有改变。
Python和java相反,只有引用传递。不过,Python的引用传递很有意思,改变实参基本类型的值不会影响形参,这是因为指了个新的。

数据类型和内存分配

基础数据类型(Value type)直接在栈(stack)空间分配,方法的形式参数,直接在栈空间分配,当方法调用完成后从栈空间回收。

引用数据类型,需要用new来创建,既在栈空间分配一个地址空间(reference),又在堆空间分配对象的类变量(object)。方法的引用参数,在栈空间分配一个地址空间,并指向堆空间的对象区,当方法调用完成后从栈空间回收。

静态变量在heap的方法区储存。

类成员实例变量储存在heap,证明了之前成员变量性能低的猜想。

JVM细节

每一个Java应用都唯一对应一个JVM实例,每一个实例唯一对应一个堆,而每个线程包含一个栈区

类 包 对象

java的getter setter就是狗屎

import

实现import as的技巧 实现导入同名类
import com.text.Formatter;
private Formatter textFormatter;
private com.json.Formatter jsonFormatter;

import static导入可以导入类的静态成员,但垃圾java缺少as的支持使得污染问题十分严重

构造方法

如果签名一致,若子类构造器没有显式调用父类构造器,将隐式调用。

初始化顺序: 静态初始化块-普通初始化块-构造器

Java 学习笔记 #1

by kenvix @ 2018/11/06

Lambda (#1) ->

变量作用域: lambda 表达式只能引用标记了 final 的外层局部变量,这就是说不能在 lambda 内部修改定义在域外的局部变量,否则会编译错误。

声明和使用

1
2
3
4
5
6
7
8
9
10
@FunctionalInterface
interface excited {
void gg(String message);
}

public static void main(String[] args) {
excited fff = message -> System.out.println("lambda block called");

fff.gg("fuck!!!");
}

此接口要求必须是函数式接口,如果其中有两个方法则lambda表达式会编译错误。但java8的新特性如许实现如下写法:

1
2
3
4
5
6
interface MathOperation {
int operation(int a, int b);
default int addition(int a, int b){
return a+b;
}
}

泛型

基本类型不能作为类型参数

泛形要求能包容的是对象类型,而基本类型在java里不属于对象
但是基本类型都有其包装类型,也就是对象类型

大括号

1. 作用域

创建一个新的作用于防止变量污染

2. 声明匿名类

1
2
3
new Object() {
//content of anymous class
};

3. 类的初始化块

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
import java.util.HashMap;

public class Test {
private static HashMap<String, String> map = new HashMap<String, String>() {
{
put("Name", "June");
put("QQ", "2572073701");
}
}; //可以在初始化时为HASHMAP赋值

public int nonStatic;

static { //静态块
System.out.println("Static block called");
}

{ //类的初始化块1
System.out.println("Init block called");
}

Test() {
System.out.println("Constrator block called");
}

{ //类的初始化块2
nonStatic = 555;
System.out.println("Init2 block called");
}

public void nmbd() {}

static {
System.out.println("Static2 block called");
}
}

OUTPUT:

1
2
3
4
5
Static block called
Static2 block called
Init block called
Init2 block called
Constrator block called

结合匿名类使用:

1
2
3
4
5
new Object() {
{
System.out.println("called!");
}
};

在Win10 Pro下挂载NFS(网络文件系统)

注意:Win10 Creators Update前只有Win10企业版可以挂载NFS, Creators Update后专业版也可挂载NFS了。

 

安装

按Win+R输入OptionalFeatures,勾选”NFS服务”

不需要勾选“管理工具”,那玩意是个废物,非WinServer只能靠命令行挂载NFS。

装好后按Win+R输入cmd

Nginx 反向代理 Aria2 JSONRPC

给Aria2服务器所用的SSL证书往往不支持Aria2所使用的6800端口,而80/443端口还要提供HTTP服务,为此就需要用Nginx来实现同时提供HTTP和Aria2 JSONRPC服务了。

目前已经测试通过并部署到了生产服务器,本文只做一个记录。

最终效果:

(Android6.0~9.0) 清除锁屏密码

如果手机已经Root并且开了ADB调试并且以前授权过要连接的电脑,则直接连该电脑即可。

如果手机未Root但刷入了TWRP或CWM等Recovery,则需要重启后进recovery,然后连电脑。

然后运行以下命令即可:

1
2
3
4
5
6
adb shell
rm /data/system/gallery_private.key
rm /data/system/gatekeeper.password.key
rm /data/system/gatekeeper.pattern.key
rm /data/system/gesture.key
reboot

也许会提示文件不存在,忽略即可。

重启后手机将没有锁屏密码。

什么?你加密了手机分区?格式化吧。

WordPress 更换站点地址后批量修改文章/评论中的旧地址

仅作记录,不建议使用。

运行以下代码即可:

前一个地址是要替换的旧地址

后一个地址是新地址

修复一加3/3T因固件过老导致刷入ROM时提示错误7的问题

博主在刷入Oneplus3 H2OS Openbeta 7后再刷LineageOS遇到了“Comparing TZ version TZ.BF.X.X-X.X.XXXX to TZ.BF.X.X-X.X.XXXX assert failed”报错

原因是当前手机固件版本过低或过高,第三方ROM不兼容。

我们知道,原厂ROM刷机包一般都会带有完整的固件,位于刷机包内 firmware-update 文件夹,可以直接提取这里面的固件,然后使用 fastboot flash 分区名 固件路径,其中分区名就是你看到的文件名再去掉扩展名

于是博主准备使用fastboot刷入固件,但又遇到了以下报错:

fastboot flash tz tz.mbn

target reported max download size of 440401920 bytes

sending ‘tz’ (1628 KB)…

OKAY [ 0.080s]

writing ‘tz’…

FAILED (remote: Partition flashing is not allowed)

finished. total time: 0.118s
(心情复杂.jpg)

然后博主突然想到recovery也可以刷入固件,抱着试一试的心态,做了一个固件刷机包

 

wow! 真的成功了哎,现在可以刷LineageOS了

修复Android DM-Verity 警告

刷入某些ROM可能导致手机在引导时弹出DM-Verity警告,警告内容为

The dm-verity is not started in enforcing mode ….

修复方法:重开DM-Verity然后再禁用。

操作步骤:

1.连电脑,进fastboot

2.输入以下代码:

1
2
3
4
fastboot oem disable_dm_verity
fastboot oem enable_dm_verity
fastboot oem disable_dm_verity
fastboot reboot

贴吧云签到 资源索引(下载|文档|插件)

贴吧云签到在[email protected]和Github均有仓库,任选(国内推荐[email protected])。

云签到主程序

[email protected] Github

云签到插件库

[email protected] Github

云签到扩展库

[email protected] Github

云签到开发文档

[email protected] Github

 

继续监控!使用树莓派+Motion实现实时视频监控并通过浏览器查看

之前我们已经实现了使用树莓派实现定时拍照监控并发送邮件到邮箱,但是定时拍照有两个缺点:

1.拍照每5min才进行一次,这中间会错过很多东西;提高拍照频率又会占用太多存储空间

2.不具有即时性。有时候你想查看这个时候的监控,却得等一小时后才能看,因为邮件还没发送。

所以我们还需要视频监控

首先确保手上有下列东西:

1.树莓派(以下简称RPI)一个

2.一个USB免驱摄像头,支持YUY2或者JPEG均可(JPEG最佳)。RPICamera没试过

博主的配置: RPI3b 一个废弃的YUY2摄像头