Javascript中一些可能是用较少的语法

set/get

1
var data = {
	items: ['a', 'b', 'c'],
	get length () {
		return this.items.length;
	},
	set first (val) {
		this.items[0] = val;
	}
};
console.log(data.length); // 3
data.length = 4; // 严格模式下报错:Uncaught TypeError: Cannot set property length of #<Object> which has only a getter(…)
console.log(data.first = 'd');
console.log(data.items); // ["d", "b", "c"]

var MyDate = function() {}

defineGetter/defineSetter

1
var data = {
	items: ['a', 'b', 'c']
};
data.__defineGetter__('length', function() {return this.items.length;});
data.__defineSetter__('first', function(val) {this.items[0] = val;})
console.log(data.length); // 3
console.log(data.first = 'd');
console.log(data.items); // ["d", "b", "c"]

Object.freeze

将某个对象冻住,好形象。

1
var a = {a:1, b: 2}; 
Object.freeze(a); 
a.c =3;
console.log(a); // {a: 1, b: 2}

Object.defineProperty

1
var obj1 = {};
Object.defineProperty(obj1, "x", { value: 42, writable: false });
obj1.x = 9; // 严格模式下抛出TypeError错误
console.log(obj1.x); // 42

Object.preventExtensions

1
// 给不可扩展对象的新属性赋值
var fixed = {};
Object.preventExtensions(fixed);
fixed.newProp = "ohai"; // 严格模式下抛出TypeError错误
console.log(fixed); // {}

Function

1
console.log(new Function('a', 'b', 'return a + b;')(1, 2)) // 3

npm命令使用

npm install will install both “dependencies” and “devDependencies”

npm install --production will only install “dependencies”

npm install --dev will only install “devDependencies”

nginx配置

全局配置

user

用于指定nginx进程运行用户以及用户组,默认情况下将使用与用户名相同的组,除非编译时指定–user=USER和–group=GROUP

worker_processes

用于指定nginx的进程数,一般设置为与CPU核数一致即可。

error_log

用于指定全局错误日志文件,日志错误级别包括debug,info,notice,warn,error,crit,日志的信息量由debug到crit递减。

nginx支持为每个虚拟主机配置不同的日志文件,如果在编译安装的时候加入–with-debug参数,可以使用以下配置:

1
error_log LOGFILE [debug_core | debug_alloc | debug_mutex | debug_event | debug_http | debug_imap];

error_log off并不能关闭日志记录,而会将日志文件写入另一个文件名为off的文件中,如果你想关闭错误日志功能 ,应使用以下配置:

1
error_log  /dev/null crit;

1
#user  nobody;
worker_processes  auto;

#error_log  logs/error.log;
#error_log  logs/error.log  notice;
#error_log  logs/error.log  info;

#pid        logs/nginx.pid;

events {
    worker_connections  1024;
    multi_accept on;
}

http {
    include       mime.types;
    default_type  application/octet-stream;

    server_tokens   off;
    sendfile        on;
    tcp_nopush      on;
    tcp_nodelay     on;

    keepalive_timeout  65;
    
    server {
        listen 80;
        server_name local.tms.shenba.com;

        location / {
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
            proxy_buffering off;
            proxy_pass           http://localhost:3445;
        }

        
    }

    server {
        listen 80;
        server_name local.h5.shenba.com;

        location / {
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
            proxy_buffering off;
            proxy_pass           http://localhost:3446;
        }
    }

    server {
        listen 80;
        server_name local.h5statics.shenba.com;

        root /Users/CoderQ/shenba/code/h5statics.shenba.com;
    }

    server {
        listen 80;
        server_name local.dian.shenba.com;
        #access_log /var/log/nginx/node_h5site.log
        location / {
            proxy_set_header    X-Real-IP           $remote_addr;
            proxy_set_header    X-Forwarded-For     $proxy_add_x_forwarded_for;
            proxy_set_header    Host                $http_host;
            proxy_set_header    X-NginX-Proxy       true;
            proxy_set_header    Connection          "";
            proxy_http_version  1.1;
            proxy_pass          http://localhost:3444;
        }
    }
    server {
        listen       80;
        server_name  local.dstatics.shenba.com;

        root   /Users/CoderQ/shenba/code/dstatics.shenba.com;

        #字体跨域
        location ~* \.(eot|ttf|woff|js)$ {
            add_header Access-Control-Allow-Origin *;
        }
    }

    # another virtual host using mix of IP-, name-, and port-based configuration
    #
    #server {
    #    listen       8000;
    #    listen       somename:8080;
    #    server_name  somename  alias  another.alias;

    #    location / {
    #        root   html;
    #        index  index.html index.htm;
    #    }
    #}


    # HTTPS server
    #
    #server {
    #    listen       443 ssl;
    #    server_name  localhost;

    #    ssl_certificate      cert.pem;
    #    ssl_certificate_key  cert.key;

    #    ssl_session_cache    shared:SSL:1m;
    #    ssl_session_timeout  5m;

    #    ssl_ciphers  HIGH:!aNULL:!MD5;
    #    ssl_prefer_server_ciphers  on;

    #    location / {
    #        root   html;
    #        index  index.html index.htm;
    #    }
    #}

}

通过OpenSSL创建证书文件构建https服务

前言

以前用node.js构建过https服务,很简单,就是把两个文件的路径放在代码里,把http协议换成https就搞定了。不过今天我收到的是一个文件夹,两个文件怎么用都报错,于是有了自己生成证书文件来证实问题出在哪里的想法。最后发现问题在于这个文件夹里全是—–BEGIN CERTIFICATE—–的文件,找不到一个—–BEGIN RSA PRIVATE KEY—–的文件。

OpenSSL生成证书

  • 创建openssl.cnf文件

    1
    [req]  
        distinguished_name = req_distinguished_name  
        req_extensions = v3_req  
      
        [req_distinguished_name]  
        countryName = Country Name (2 letter code)  
        countryName_default = CN  
        stateOrProvinceName = State or Province Name (full name)  
        stateOrProvinceName_default = BeiJing  
        localityName = Locality Name (eg, city)  
        localityName_default = YaYunCun  
        organizationalUnitName  = Organizational Unit Name (eg, section)  
        organizationalUnitName_default  = Domain Control Validated  
        commonName = Internet Widgits Ltd  
        commonName_max  = 64  
      
        [ v3_req ]  
        # Extensions to add to a certificate request  
        basicConstraints = CA:FALSE  
        keyUsage = nonRepudiation, digitalSignature, keyEncipherment  
        subjectAltName = @alt_names  
      
        [alt_names]  
    	#注意这个IP.1的设置,IP地址需要和你的服务器的监听地址一样
        IP.1 = 127.0.0.1
  • 为CA生成私钥

    1
    openssl genrsa -out ca-key.pem -des 1024
  • 通过CA私钥生成CSR

    1
    openssl req -new -key ca-key.pem -out ca-csr.pem
  • 通过CSR文件和私钥生成CA证书

    1
    openssl x509 -req -in ca-csr.pem -signkey ca-key.pem -out ca-cert.pem
  • 通过服务器私钥文件和CSR文件生成服务器证书

    1
    openssl x509 -req -CA ca-cert.pem -CAkey ca-key.pem -CAcreateserial -in server-csr.pem -out server-cert.pem -extensions v3_req -extfile openssl.cnf

node.js服务端

1
var https = require('https');
var fs = require('fs');

var options = {
	key: fs.readFileSync('./keys/server-key.pem'),
	// ca: [fs.readFileSync('./keys/ca-cert.pem')],
	cert: fs.readFileSync('./keys/server-cert.pem')
};

https.createServer(options,function(req,res){
	res.writeHead(200);
	res.end('hello world\n');
}).listen(3000,'127.0.0.1');

参考文献

https://cnodejs.org/topic/54745ac22804a0997d38b32d

html中UTF8编码的解码

我们写爬虫爬回来的一些页面可能是编码后的utf8码,这时候我们需要对他们进行解码

1
var code10, code16, zh;

code10 = '&#22825;&#22530;&#21521;&#24038;,&#28145;&#22323;&#21521;&#21491;';

zh = code10.replace(/&#(\d+);/g, function($, $1) {return String.fromCodePoint($1)});

console.log(zh);

code16 = zh.replace(/[^\u0000-\u00ff]/g, function($) {return '&#x' + $.codePointAt(0).toString(16) + ';';});

console.log(code16);

zh = code16.replace(/&#x(\w+);/g, function($, $1) {return String.fromCodePoint(parseInt($1, 16))});

console.log(zh);

mongodb的文档如何通过自己的某些字段更新文档的方法

仅仅改变Key

如果你的值没有问题,只是你的key出现了问题,需要修改key,可以使用$rename来做简单的处理

1
2
3
4
5
// init
db.events.insert({ 'lat': 1, 'lon': 2, someotherdata: [] })
db.events.insert({ 'lat': 4, 'lon': 1, someotherdata: [] })
// doit
db.events.update({}, {$rename: {'lat': 'coords.lat', 'lon': 'coords.lon'}}, false, true)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
// result
db.events.find()
{
"_id" : ObjectId("5113c82dd28c4e8b79971add"),
"coords" : {
"lat" : 1,
"lon" : 2
},
"someotherdata" : [ ]
}
{
"_id" : ObjectId("5113c82ed28c4e8b79971ade"),
"coords" : {
"lat" : 4,
"lon" : 1
},
"someotherdata" : [ ]
}

修复Key和Value

如果你的value也出现问题,那么仅仅rename是无济于事的,你可以用下面的方法来处理整个collection。

1
2
3
4
5
6
7
8
9
10
11
12
13
db.events.find().snapshot().forEach(
function (e) {
// update document, using its own properties
e.coords = { lat: e.lat, lon: e.lon };

// remove old properties
delete e.lat;
delete e.lon;

// save the updated document
db.events.save(e);
}
)

查看stackoverflow

javascript实现合并排序

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
var merge = function(ary, p, q, r) {
// eg. ary = [4, 1], p = 0, q = 0, r = 1
var l_ary = ary.slice(p, q + 1);
var r_ary = ary.slice(q + 1, r + 1);
var b_ary;

while (l_ary.length && r_ary.length) {
ary[p++] = l_ary[0] <= r_ary[0] ? l_ary.shift() : r_ary.shift();
}

b_ary = l_ary.length ? l_ary : r_ary;
while (b_ary.length) {
ary[p++] = b_ary.shift();
}

console.log(ary);
}

var merge_sort = function(ary, s, e) {
var m;
if (s === e) return;
m = Math.floor((s + e) / 2);

merge_sort(ary, s, m);
merge_sort(ary, m + 1, e);
merge(ary, s, m, e);
}

var do_merge_sort = function() {
var ary = [4, 3, 7, 1, 9, 2, 6, 5];

console.log(ary);
merge_sort(ary, 0, ary.length - 1);

console.log(ary);
}

do_merge_sort();

用cmake安装opencv遇到缺少ippicv-macosx-*.*文件的解决方案

  1. 既然出错,那么你一定可以看到报错提示,大致如下。这里面你收获了第一个关键信息expected hash: [4ff1fde9a7cfdfe7250bfcd8334e0f2f]

    1
    for file: [/Users/CoderQ/Downloads/opencv-3.1.0/3rdparty/ippicv/downloads/macosx-4ff1fde9a7cfdfe7250bfcd8334e0f2f/ippicv_macosx_20151201.tgz]
      expected hash: [4ff1fde9a7cfdfe7250bfcd8334e0f2f]
        actual hash: [cc09c2a46b5dd28acea8e1e78e296670]
             status: [28;"Timeout was reached"]
  2. 上搜索引擎搜4ff1fde9a7cfdfe7250bfcd8334e0f2f,你会发现第一个搜索结果指向了源码地址

  3. 代码里OPENCV_ICV_PACKAGE_HASH这个变量指向了4ff1fde9a7cfdfe7250bfcd8334e0f2f

  4. 之后你会找到这行代码,他告诉你这个URL地址还需要另一个变量OPENCV_ICV_URL

    1
    file(DOWNLOAD "${OPENCV_ICV_URL}/${OPENCV_ICV_PACKAGE_NAME}" "${OPENCV_ICV_PACKAGE_ARCHIVE}"
  5. 之后根据源码你可以拼出这个地址

    1
    https://raw.githubusercontent.com/Itseez/opencv_3rdparty/81a676001ca8075ada498583e4166079e5744668/ippicv/ippicv_macosx_20151201.tgz
  6. 把文件下载后放在提示的地址,重新安装。

    1
    /Users/CoderQ/Downloads/opencv-3.1.0/3rdparty/ippicv/downloads/macosx-4ff1fde9a7cfdfe7250bfcd8334e0f2f/ippicv_macosx_20151201.tgz

Unicode字符处理

最近做爬虫程序,偶尔会在返回的内容中看到一堆类似这样的东西&#22825;&#22530;&#21521;&#24038;,&#28145;&#22323;&#21521;&#21491;,一时间不知道怎么把它们转成中文。于是上网求救,发现解决方案后感觉so easy。其实很多东西不明白之前都很难,明白了就很简单,我是不是在说废话呢???

其实这串字符中的数字就是对应unicode字符的十进制表示方式,所以我们只要通过String.fromCodePoint进行简单的转化就可以得到想要的结果了。根据网友的提示,返回的内容还有可能是十六进制的,于是我自己写了个例子,备忘。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
var code10, code16, zh;

code10 = '&#22825;&#22530;&#21521;&#24038;,&#28145;&#22323;&#21521;&#21491;';

zh = code10.replace(/&#(\d+);/g, function($, $1) {
return String.fromCodePoint($1)
});

console.log(zh);

code16 = zh.replace(/[^\u0000-\u00ff]/g, function($) {
return '&#x' + $.codePointAt(0).toString(16) + ';';
});

console.log(code16);

zh = code16.replace(/&#x(\w+);/g, function($, $1) {
return String.fromCodePoint(parseInt($1, 16))
});

console.log(zh);

C语言基础

指针

指针(Pointer)是编程语言中的一个对象,利用地址,它的值直接指向存在电脑存储器中另一个地方的值。

1
#include "stdio.h"

int main(int argc, char const *argv[])
{
	char* c = "123"; // c是一个指针变量,指向"123"这个字符串的内存地址
	printf("%s\n", c); // 打印出c指针指向的字符串
	printf("%c\n", *c); // 打印出c指针指向的第一个字符

	short s = 123; // 定义一个短整形变量s
	short* p = &s; // 定义一个短整形指针,并让指针指向s所在的地址
	printf("%u\n", *p); // 输出p指针所指向的内存快

	return 0;
}

很多书籍,喜欢把*号放在变量前面,但是这容易让初学者误解,其实*放在类型后面或变量前面都是没问题的。如果加*,例如char* c,那么c就是一个指针变量,如果要取出它对应的值,必须使用*c,这样好理解很多了。如果写成char *c就容易搞不清楚定义的是个啥了。

,