2018年2月

感觉elasticsearch 的 phpclient 没有自己写的curl快,因此封装curl类。

<?php
/**
 * Created by PhpStorm.
 * User: shw
 * Date: 2017/12/28
 * Time: 10:37
 */
class Elasticsearch{
    private $host = "192.168.0.186";
    private $port = "9200";
    private $user = "elastic";
    private $password = "3Y~KyvQ1nkt~I7%PZU^3";
    private $es = null;
    public function __construct(){
        header("Content-type: text/html; charset=utf-8");
        if($this->es == null){
            $this->es ="$this->user:$this->password@$this->host:$this->port";
        }
    }
    public function curl_post($index_name,$type,$data){
        $url = $this->es.'/'.$index_name.'/'.$type.'/_search';
        $post_data = json_encode($data,JSON_UNESCAPED_UNICODE);
        $header = array();
        $header[] = 'Accept:application/json';
        $header[] = 'Content-Type:application/json;charset=utf-8';
        $ch = curl_init();
        curl_setopt($ch, CURLOPT_URL, $url);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
        curl_setopt($ch, CURLOPT_POST, 1);
        curl_setopt($ch, CURLOPT_POSTFIELDS,$post_data);
        curl_setopt($ch,CURLOPT_HTTPHEADER,$header);
        $result = curl_exec($ch);
        curl_close($ch);
        return $result;

    }

    public function create_index_mapping($index_name,$doctype,$mapping){
        $url = $this->es.'/'.$index_name.'/'.$doctype.'/_mapping?pretty';
        $post_data = json_encode($mapping,JSON_UNESCAPED_UNICODE);
        $header = array();
        $header[] = 'Accept:application/json';
        $header[] = 'Content-Type:application/json;charset=utf-8';
        $ch = curl_init();
        curl_setopt($ch, CURLOPT_URL, $url);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
        curl_setopt($ch, CURLOPT_POST, 1);
        curl_setopt($ch, CURLOPT_POSTFIELDS,$post_data);
        curl_setopt($ch,CURLOPT_HTTPHEADER,$header);
        $result = curl_exec($ch);
        curl_close($ch);
        return $result;
    }

    public function remove_index($index_name){
        $url = $this->es.'/'.$index_name;
        $post_data = array(
        );
        $header = array();
        $header[] = 'Accept:application/json';
        $header[] = 'Content-Type:application/json;charset=utf-8';

        $ch = curl_init();
        curl_setopt($ch, CURLOPT_URL, $url);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
        curl_setopt($ch, CURLOPT_CUSTOMREQUEST, "DELETE");
        curl_setopt($ch,CURLOPT_HTTPHEADER,$header);
        $result = curl_exec($ch);
        curl_close($ch);
        return $result;
    }

    /**
     * [create_index 创建索引库]
     * @param  [string] $index_name [名称]
     * @return [json]             [结果]
     */
    public function create_index($index_name){
        $url = $this->es.'/'.$index_name;
        $post_data = array(
        );
        $header = array();
        $header[] = 'Accept:application/json';
        $header[] = 'Content-Type:application/json;charset=utf-8';

        $ch = curl_init();
        curl_setopt($ch, CURLOPT_URL, $url);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
        curl_setopt($ch, CURLOPT_CUSTOMREQUEST, "PUT");
        $result = curl_exec($ch);
        curl_close($ch);
        return $result;
    }

    /**
     * [insert 添加索引数据 ]
     * @param  [type] $index_name [description]
     * @param  [type] $type       [description]
     * @param  [type] $data       [description]
     * @param  [type] $_id        [description]
     * @return [type]             [description]
     */
    public function insert($index_name,$type,$data,$_id){
        $url = $this->es.'/'.$index_name.'/'.$type.'/'.$_id;
        $ch = curl_init();
        $header = array();
        $header[] = 'Accept:application/json';
        $header[] = 'Content-Type:application/json;charset=utf-8';
        curl_setopt($ch, CURLOPT_URL, $url);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
        curl_setopt($ch, CURLOPT_CUSTOMREQUEST, "PUT");
        curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($data,JSON_UNESCAPED_UNICODE));
        curl_setopt($ch,CURLOPT_HTTPHEADER,$header);
        $result = curl_exec($ch);
        curl_close($ch);
        return $result;
    }

    /**
     * [update 修改索引数据]
     * @param  [type] $index_name [description]
     * @param  [type] $type       [description]
     * @param  [type] $data       [description]
     * @param  [type] $_id        [description]
     * @return [type]             [description]
     */
    public function update($index_name,$type,$data,$_id){
        $url = $this->es.'/'.$index_name.'/'.$type.'/'.$_id.'/_update';
        $ch = curl_init();
        $header = array();
        $header[] = 'Accept:application/json';
        $header[] = 'Content-Type:application/json;charset=utf-8';
        curl_setopt($ch, CURLOPT_URL, $url);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
        curl_setopt($ch, CURLOPT_POST, 1);
        curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($data,JSON_UNESCAPED_UNICODE));
        curl_setopt($ch,CURLOPT_HTTPHEADER,$header);
        $result = curl_exec($ch);
        curl_close($ch);
        return $result;
    }

    public function delete($index_name,$type,$_id){
        $url = $this->es.'/'.$index_name.'/'.$type.'/'.$_id;
        $post_data = array(
        );
        $header = array();
        $header[] = 'Accept:application/json';
        $header[] = 'Content-Type:application/json;charset=utf-8';

        $ch = curl_init();
        curl_setopt($ch, CURLOPT_URL, $url);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
        curl_setopt($ch, CURLOPT_CUSTOMREQUEST, "DELETE");
        curl_setopt($ch,CURLOPT_HTTPHEADER,$header);
        $result = curl_exec($ch);
        curl_close($ch);
        return $result;
    }

    /**
     * [搜索]
     * @param  [string] $index_name [索引名称]
     * @param  [array] $data       [条件]
     * @param  [int] $size       [返回行数]
     * @param  [array] $sort       [排序]
     * @return [json]             [结果]
     */
    public function search($index_name,$doctype,$data){
        return $this->curl_post($index_name,$doctype,$data);
    }


    //match_phrase完全匹配不分词  match任意一词匹配
    public function demo(){
        $select = array(
                "bool" => array(
                    "should"=>array(
                        "match" => array('title'=>'电视机')
                    )
                )
        );
        $data = array(
            'size' => 10,
            'query' => $select,
            'sort'=> ['_id'=>['order'=>'asc']]
        ); 
        print_r(json_decode($this->curl_post('chinacms','cms_news_main',$data),true));
    }

    public function demo2(){
        $select = array(
                "bool" => array(
                    "must" => array(
                        "match_phrase" => array('title'=>'电视机'),
                    ),

                    "filter" => array(
                        "terms" => array(
                            "status" => [2,3]
                        )
                    )
                )
        );
        $data = array(
            'size' => 10,
            'query' => $select,
            'sort'=> ['_id'=>['order'=>'asc']]
        ); 
        print_r(json_decode($this->curl_post('chinacms','cms_news_main',$data),true));
    }

    public function demo3(){
        $select = array(
                    "bool" => array(
                        "must" => array(
                            array("match_phrase" => array('title'=>'电视机')),
                            array("term" => array("hangye_id"=>122)),
                            //array("term" => array("status"=>3))
                            array("terms" => array("status"=>[2,3]))
                        )
                    )
        );
        $data = array(
            'size' => 10,
            'query' => $select,
            'sort'=> ['_id'=>['order'=>'asc']]
        ); 
        print_r(json_decode($this->curl_post('chinacms','cms_news_main',$data),true));
    }

    public function get_by_itemid($itemid){
        $select = array(
                    "bool" => array(
                        "must" => array(
                            array("term" => array("itemid"=>$itemid))
                        )
                    )
        );
        $data = array(
            'size' => 10,
            'query' => $select,
            'sort'=> ['_id'=>['order'=>'asc']]
        ); 
        print_r(json_decode($this->curl_post('chinacms','cms_news_main',$data),true));
    }
}

$es = new Elasticsearch();
//$es->remove_index('chinacms');

//创建一个索引chinacms
//$result = $es->create_index('chinacms');
//设置字段结构
//itemid,hangye_id,status,userid,title,sources,class
// $mapping = array(
//         'cms_news_main' => array(
//                 "properties" => array(
//                         "itemid" => ['type'=>'integer'],
//                         "hangye_id" => ['type'=>'integer'],
//                         "status" => ['type'=>'integer'],
//                         "userid" => ['type'=>'integer'],
//                         "title" => ['type'=>'text'],
//                         "sources" => ['type'=>'text'],
//                         "class" => ['type'=>'text']
//                     )
//             )
//     );
// $result = $es->create_index_mapping('chinacms','cms_news_main',$mapping);
//return { "acknowledged" : true }
//-----------------------------------------------------------------------
//
//创建产品索引 cms_sell_main
//itemid,title,hangye_id,status,sources,catid,userid

// $sell_mapping = array(
//     'cms_sell_main' => array(
//             "properties" => array(
//                     "itemid" => ['type'=>'integer'],
//                     "hangye_id" => ['type'=>'integer'],
//                     "status" => ['type'=>'integer'],
//                     "userid" => ['type'=>'integer'],
//                     "title" => ['type'=>'text'],
//                     "sources" => ['type'=>'text'],
//                     "catid" => ['type'=>'integer']
//                 )
//         )
//     );

// $es->create_index('product');
// $result = $es->create_index_mapping('product','cms_sell_main',$sell_mapping);

//创建图库索引库
//
//

$photo_mapping = array(
    'cms_photo_main' => array(
            "properties" => array(
                    "itemid" => ['type'=>'integer'],
                    "hangye_id" => ['type'=>'integer'],
                    "status" => ['type'=>'integer'],
                    "userid" => ['type'=>'integer'],
                    "title" => ['type'=>'text'],
                    "sources" => ['type'=>'text'],
                    "catid" => ['type'=>'integer'],
                    "brandusername" => ['type'=>'text'],
                    "lanmu" => ['type'=>'text']
                )
        )
    );
//$result = $es->remove_index('photo');
$es->create_index('photo');
$result = $es->create_index_mapping('photo','cms_photo_main',$photo_mapping);

//$es->demo3();
//$result = $es->create_index('hq');
/**
$doctype = "user";
$id = 15;
$data = array(
        'username'=>'李绮婷',
        'userage'=>16,
        'usertel'=>'13779531261'
    );
$result = $es->insert('hq',$doctype,$data,$id);
**/
//
//$result = $es->delete('hq','user',11);
//
/**
$doctype = "user";
$id = 15;
$data = array(
        'doc' => array(
            //'username'=>'李绮婷',
            //'userage'=>16,
            'usertel'=>'123456789'
        )
    );
$result = $es->update('hq',$doctype,$data,$id);
**/

//$result = $es->get_by_itemid(1014287);
print_r($result);

#20180710补充,需要注意insert方法和update方法传的数组不一样 ,如果使用了insert方法一要样的数组
#需要调整update方法为 如下
/**
     * [update 修改索引数据]
     * @param  [type] $index_name [description]
     * @param  [type] $type       [description]
     * @param  [type] $data       [description]
     * @param  [type] $_id        [description]
     * @return [type]             [description]
     */
    public function update($index_name,$type,$data,$_id){
        $data  = array(
            'doc'=>$data
        );
        $url = $this->es.'/'.$index_name.'/'.$type.'/'.$_id.'/_update';
        $ch = curl_init();
        $header = array();
        $header[] = 'Accept:application/json';
        $header[] = 'Content-Type:application/json;charset=utf-8';
        curl_setopt($ch, CURLOPT_URL, $url);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
        curl_setopt($ch, CURLOPT_POST, 1);
        curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($data,JSON_UNESCAPED_UNICODE));
        curl_setopt($ch,CURLOPT_HTTPHEADER,$header);
        $result = curl_exec($ch);
        curl_close($ch);
        return $result;
    }

python初始化索引数据

#!/usr/bin/python
#coding:utf-8
import urllib2
import MySQLdb
import threading
import sys
import re
import os
import json
from elasticsearch import Elasticsearch
reload(sys) 
sys.setdefaultencoding('utf-8')

def db_obj():
    conf = ['localhost','root','pwd','chinacms4']
    return MySQLdb.connect(conf[0],conf[1],conf[2],conf[3],charset="utf8")

es = Elasticsearch( "127.0.0.1:9200",http_auth=('elastic', '3Y~KyvQ1nkt~I7%PZU^3'))

def es_put(index_name,_id,type_name,data):
    global es
    try:
        es.index( index=index_name,doc_type=type_name,id=_id,body=data )
        print str(_id)+"add success!"
    except Exception,e:
        print repr(e)
def http_put(url,data):
    request = urllib2.Request(url,data)
    request.add_header('User-Agent', "Mozilla/5.0 (Windows NT 6.1; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/59.0.3071.115 Safari/537.36")
    try:
        request = urllib2.urlopen(request)
        rv = request.read()
        request.close()
        return rv
    except Exception,e:
        print "............................................................................................"
        print url
        print data
        print e
        print "............................................................................................"
def strip_tags(html):
    #过滤
    dr = re.compile(r'<([^>]+)>',re.S)
    html = dr.sub('',html)
    html = re.sub(r'[\n]+',r'', html, flags=re.S)
    html = html.replace('\t','').replace('\n','').replace(' ','')
    html = html.replace(unichr(8206).encode('utf-8'), '') \
        .replace(unichr(8207).encode('utf-8'), '') \
        .replace(unichr(8205).encode('utf-8'), '') \
        .replace(unichr(8204).encode('utf-8'), '') \
        .replace(unichr(8234).encode('utf-8'), '') \
        .replace(unichr(8237).encode('utf-8'), '') \
        .replace(unichr(8238).encode('utf-8'), '') \
        .replace(unichr(8236).encode('utf-8'), '') \
        .replace(unichr(8302).encode('utf-8'), '') \
        .replace(unichr(8303).encode('utf-8'), '') \
        .replace(unichr(8299).encode('utf-8'), '') \
        .replace(unichr(8298).encode('utf-8'), '') \
        .replace(unichr(8301).encode('utf-8'), '') \
        .replace(unichr(8300).encode('utf-8'), '') \
        .replace(unichr(30).encode('utf-8'), '') \
    .replace(unichr(13).encode('utf-8'), '') \
    .replace(unichr(299).encode('utf-8'), '') \
    .replace(unichr(230).encode('utf-8'), '') \
    .replace(unichr(228).encode('utf-8'), '') \
    .replace(unichr(102).encode('utf-8'), '') \
    .replace(unichr(232).encode('utf-8'), '') \
    .replace(unichr(233).encode('utf-8'), '') \
    .replace(unichr(110).encode('utf-8'), '') \
    .replace(unichr(229).encode('utf-8'), '') \
        .replace(unichr(31).encode('utf-8'), '') 
    html = s = re.compile('[\\x00-\\x08\\x0b-\\x0c\\x0e-\\x1f]').sub('',html) 
    return html.strip()

def create_index(start,end):
        f = open('/scripts/news_title.log.txt', 'w')
        for i in range(start,end):
                db = db_obj()
                cur = db.cursor()
                sql = "select itemid,hangye_id,status,userid,title,sources,class from cms_news_main where itemid = %s"%i;
                cur.execute(sql)
                result = cur.fetchone()
                if result != None:
                        data = '{"itemid":"'+str(result[0])+'","hangye_id":"'+str(result[1])+'","status":"'+str(result[2])+'","userid":"'+str(result[3])+'","title":"'+str(result[4])+'","sources":"'+str(result[5])+'","class":"'+str(result[6])+'"}'
                        try:
                                es.index(index='caijiqi_news_title', doc_type='title', refresh=True, body=data,id=result[0])
                                print str(i)+">>>>>>>>>>>>>>>>> 添加成功"
                        except Exception,e:
                                print e
                                print >> f,str(i)+"\r\n"
                else:
                        print "itemid"+str(i)+"无数据"
                db.close()
        f.close()
#data = '{"content":"五千年的风和雨啊"}'
#es_put("chinacms4",1,"content",data)           
#es.index(index='blog', doc_type='blog_content', refresh=True, body=data,id=1)
#print data
#es.index(index="chinacms4",doc_type="content",data,id=result[0])

#创建300个线程

for i in range(0,100):
   threading.Thread(target=create_index,args=(i*10000,(i+1)*10000)).start()

#for i in range(0,30):
#        threading.Thread(target=create_index,args=(i*100000,(i+1)*100000)).start()

Composer -- PHP依赖管理的用法
安装es的php客户端autoload
composer的安装

ln -s /usr/local/php/etc/bin/php /usr/bin/php
curl -sS https://getcomposer.org/installer | php
cp composer.phar /usr/bin/composer #就能直全局接用 composer 命令了 

安装es的php客户端autoload
到一个目录下

vim composer.json

写入

{
    "require": {
        "elasticsearch/elasticsearch": "~2.0@beta"
    }
}

运行

php composer.phar install
Do not run Composer as root/super user! See https://getcomposer.org/root for details
Loading composer repositories with package information
Updating dependencies (including require-dev)
Package operations: 5 installs, 0 updates, 0 removals
  - Installing react/promise (v2.5.1): Downloading (100%)         
  - Installing guzzlehttp/streams (3.0.0): Downloading (100%)         
  - Installing guzzlehttp/ringphp (1.1.0): Downloading (100%)         
  - Installing psr/log (1.0.2): Downloading (100%)         
  - Installing elasticsearch/elasticsearch (v2.3.2): Downloading (100%)         
elasticsearch/elasticsearch suggests installing monolog/monolog (Allows for client-level logging and tracing)
Writing lock file
Generating autoload file

完成后在当前目录下会有
vendor
把vendor重命名为Elasticsearch
放到第三方扩展目录下,比如thinkcmf的simplewindCoreLibraryVendor\
引用 use CommLibElasticsearch
即可用
也可使用如下使用方法

public function es_test(){
    Vendor('Elasticsearch.autoload');
    $params['hosts'] = array(
            '192.168.0.186:9200'
    );
    $this->client = new \Elasticsearch\Client($params);
    print_r($this->client);
}

有时候国外镜像太慢,可用设置其使用国内镜像。
比如安装七牛
这样即可直接用命令,无需加 php composer.part xxx了

mv composer.phar /usr/bin/composer
composer config -g repo.packagist composer https://packagist.phpcomposer.co
composer require qiniu/php-sdk
Your version of PHP, 5.4.1, is affected by CVE-2013-6420 and cannot safely perform certificate validation, we strongly suggest you upgrade.
Do not run Composer as root/super user! See https://getcomposer.org/root for details
Using version ^7.2 for qiniu/php-sdk
./composer.json has been updated
Loading composer repositories with package information
Updating dependencies (including require-dev)
Package operations: 1 install, 0 updates, 0 removals
  - Installing qiniu/php-sdk (v7.2.3): Downloading (100%)         
Writing lock file
Generating autoload files

#确认nginx安装了 --with-http_stub_status_module

server {
    listen  *:80 default_server;
    server_name _;
    location /ngx_status 
    {
        stub_status on;
        access_log off;
        #allow 127.0.0.1;
        #deny all;
    }
}

#curl http://127.0.0.1/ngx_status
#Active connections: 161 
#server accepts handled requests
# 71431697 71431697 92371717 
#Reading: 3 Writing: 13 Waiting: 145 


#脚本ngx-status.sh

#!/bin/sh
HOST="127.0.0.1"
PORT="80"

# 检测nginx进程是否存在
function ping {
    /sbin/pidof nginx | wc -l
}
# 检测nginx性能
function active {
    /usr/bin/curl "http://$HOST:$PORT/ngx_status/" 2>/dev/null| grep 'Active' | awk '{print $NF}'
}
function reading {
    /usr/bin/curl "http://$HOST:$PORT/ngx_status/" 2>/dev/null| grep 'Reading' | awk '{print $2}'
}
function writing {
    /usr/bin/curl "http://$HOST:$PORT/ngx_status/" 2>/dev/null| grep 'Writing' | awk '{print $4}'
}
function waiting {
    /usr/bin/curl "http://$HOST:$PORT/ngx_status/" 2>/dev/null| grep 'Waiting' | awk '{print $6}'
}
function accepts {
    /usr/bin/curl "http://$HOST:$PORT/ngx_status/" 2>/dev/null| awk NR==3 | awk '{print $1}'
}
function handled {
    /usr/bin/curl "http://$HOST:$PORT/ngx_status/" 2>/dev/null| awk NR==3 | awk '{print $2}'
}
function requests {
    /usr/bin/curl "http://$HOST:$PORT/ngx_status/" 2>/dev/null| awk NR==3 | awk '{print $3}'
}
# 执行function
$1

#把监控加入到zabbix客户端中
cd /usr/local/zabbix/etc/
vim zabbix_agentd.conf
UserParameter=nginx.status[*],/scripts/ngx-status.sh $1

#测试
/usr/local/zabbix/bin/zabbix_get -s 127.0.0.1 -k 'nginx.status[ping]'

#报错 ZBX_NOTSUPPORTED: Unsupported item key.
#忘记重启生效
service zabbix_agentd restart
#测试成功
[root@localhost etc]# /usr/local/zabbix/bin/zabbix_get -s 127.0.0.1 -k 'nginx.status[ping]'
1

#导入监控模板
#我的2.4.8出现  Unknown import version
#下载后打开,修改下版本号
#<version>2.0</version>

组态汇入 » 配置模板 » 组态汇入 » 图形化介面的组态 » 配置主机 
»模板 »  添加Template App NGINX » 更新

监控模板:
zbx_export_templates.zip

参考:http://www.ttlsa.com/zabbix/zabbix-monitor-nginx-performance/

经常我们会遇到想找出不包含某个字符串的文本,程序员最容易想到的是在正则表达式里使用,^(hede)来过滤”hede”字串,但这种写法是错误的。我们可以这样写:1,但这样的正则表达式完全是另外一个意思,它的意思是字符串里不能包含‘h',‘e',‘d'三个但字符。那什么样的正则表达式能过滤出不包含完整“hello”字串的信息呢?

事实上,说正则表达式里不支持逆向匹配并不是百分之百的正确。就像这个问题,我们就可以使用否定式查找来模拟出逆向匹配,从而解决我们的问题:

复制代码 代码如下:
^((?!hede).)*$

上面这个表达式就能过滤出不包含‘hede'字串的信息。我上面也说了,这种写法并不是正则表达式“擅长”的用法,但它是可以这样用的。

解释

一个字符串是由n个字符组成的。在每个字符之前和之后,都有一个空字符。这样,一个由n个字符组成的字符串就有n+1个空字符串。我们来看一下“ABhedeCD”这个字符串:

所有的e编号的位置都是空字符。表达式(?!hede).会往前查找,看看前面是不是没有“hede”字串,如果没有(是其它字符),那么.(点号)就会匹配这些其它字符。这种正则表达式的“查找”也叫做“zero-width-assertions”(零宽度断言),因为它不会捕获任何的字符,只是判断。

在上面的例子里,每个空字符都会检查其前面的字符串是否不是‘hede',如果不是,这.(点号)就是匹配捕捉这个字符。表达式(?!hede).只执行一次,所以,我们将这个表达式用括号包裹成组(group),然后用*(星号)修饰——匹配0次或多次:

复制代码 代码如下:
((?!hede).)*。

你可以理解,正则表达式((?!hede).)*匹配字符串"ABhedeCD"的结果false,因为在e3位置,(?!hede)匹配不合格,它之前有"hede"字符串,也就是包含了指定的字符串。

在正则表达式里, ?! 是否定式向前查找,它帮我们解决了字符串“不包含”匹配的问题。

以下是一些补充:

分享下php生成随机数的三种方法,生成1-10之间的不重复随机数,php生成不重复随机数的例子,需要的朋友参考下。

在hacker news上看到regex golf,几道很有趣的正则表达式的题,有的需要用到不匹配这种匹配,比如需要匹配不包含某个单词的串。

开始正题之前,先来看看正则表达式的语法:

[abc] a或b或c

. 任意单个字符

a? 零个或一个a
2 任意不是abc的字符

s 空格

a* 零个或多个a
[a-z] a-z的任意字符

S 非空格

a+ 一个或多个a
[a-zA-Z] a-z或A-Z

d 任意数字

a{n} 正好出现n次a
^ 一行开头

D 任意非数字

a{n,} 至少出现n次a
$ 一行末尾

w 任意字母数字或下划线

a{n,m} 出现n-m次a
(...) 括号用于分组

W 任意非字母数字或下划线

a*? 零个或多个a(非贪婪)
(a|b) a或b

b 单词边界

(a)...1 引用分组
(?=a) 前面有a

(?!a) 前面没有a

B 非单词边界

正则表达式中有(?=a)和(?!a)来表示我们是否需要匹配某个东西。

所以,有需要不匹配某样内容时,就可以用(?!a)了。比如要匹配不含hello的字符串就可以这样写。

^(?!.*hello)

这里.*用来表示hello之前可能有其他的字符,为什么还要加^呢,因为如果不加的话,可能匹配到h之后的这个位置上了。

现在就可以解决regex golf上的abba这道题了。
这道题是去匹配不含abba这种形式的单词,比如abba,anallagmatic就不应该匹配上。

正则表达式代码:

^(?!.*(.)(.)21)

然后利用不匹配,还可以解决prime这道题,这道题匹配有素数个x的串,先看正则。

^(?!(xx+)1+$)

(xx+)是匹配2个及2个以上的x,(xx+)1+就是匹配重复出现2个及以上的串,所以(xx+)1+就表示了那些非素数的串,那么素数串就是除去这些非素数串,即是以上的正则表达式了。

转载自 https://www.cnblogs.com/paddygege/p/6957866.html


  1. hede
  2. abc

需求场景:

某一天电脑重装系统,安装google浏览器,要恢复收藏夹的网址。
做为开发人员,自知道google浏览器对开发人员的帮助作用。

问朋友借一下它的海外vps,然后通过xhsell连接。
在连接中配置隧道一栏。
01.jpg

然后下载浏览器扩展 SwitchyOmega_Chromium

参考 https://github.com/FelisCatus/SwitchyOmega/releases/tag/v2.5.10

配置一下:
02.jpg

就能用了,迅速登录恢复收藏夹。