用Python3提取网页中的超链接

最近有朋友给我指出,我此前写的博文《用Python提取网页中的超链接》(原文地址:http://www.sunbloger.com/article/442.html)中,给出的代码在Python3下运行报错。下面给出在Python3的代码写法:

import urllib.request
import re
 
url = 'http://www.sunbloger.com/'
 
req = urllib.request.urlopen(url)
doc = req.read()
doc = doc.decode('utf-8')
 
links = re.findall(r'href\=\"(http\:\/\/[a-zA-Z0-9\.\/]+)\"', doc)
for a in links:
    print(a)

 

阳光部落原创,更多内容请访问http://www.sunbloger.com/

汇总PHP最常见的四种排序算法

PHP最常见的四种排序算法分别是:冒泡排序法,选择排序法、插入排序法和快速排序法。下面我们就分别给出四种排序算法的实现代码,供大家参考。

1.冒泡排序法

<?php
function bubble_sort($array)
{
    $count = count($array);
    if ($count == 0) {
        return false;
    }
    for ($i=0; $i<$count; $i++) {
        for ($k=$count-1; $k>$i; $k--) {
            if ($array[$k] < $array[$k-1]) {
                $tmp = $array[$k];
                $array[$k] = $array[$k-1];
                $array[$k-1] = $tmp;
            }
        }
    }
    return $array;
}

$a = array(2, 5, 1, 3, 4);
$a = bubble_sort($a);
var_dump($a);
?>

 

2.选择排序法

<?php
function select_sort($array)
{
    $len = count($array);
    for($i=0; $i<$len-1; $i++) {
        $p = $i;
        for($j=$i+1; $j<$len; $j++) {
            if($array[$p] > $array[$j]) {
                $p = $j;
            }
        }
        if($p != $i) {
            $tmp = $array[$p];
            $array[$p] = $array[$i];
            $array[$i] = $tmp;
        }
    }
    
    return $array;
}

$a = array(2, 5, 1, 3, 4);
$a = select_sort($a);
var_dump($a);
?>

 

3.插入排序法

<?php
function insert_sort($array)
{
    $len = count($array);
    for($i=1; $i<$len; $i++) {
        $tmp = $array[$i];
        for($j=$i-1; $j>=0; $j--) {
            if($tmp < $array[$j]) {
                $array[$j+1] = $array[$j];
                $array[$j] = $tmp;
            } else {
                break;
            }
        }
    }
    
    return $array;
}

$a = array(2, 5, 1, 3, 4);
$a = insert_sort($a);
var_dump($a);
?>

 

4.快速排序法

<?php
function quick_sort($array)
{
    $len = count($array);
    if ($len <= 1) {
        return $array;
    }
    
    $base = $array[0];
    
    $left = array();
    $right = array();
    for ($i=1; $i<$len; $i++) {
        if($base > $array[$i]) {
            $left[] = $array[$i];
        } else {
            $right[] = $array[$i];
        }
    }
    $left = quick_sort($left);
    $right = quick_sort($right);
    
    return array_merge($left, array($base), $right);
}

$a = array(2, 5, 1, 3, 4);
$a = quick_sort($a);
var_dump($a);
?>

 

阳光部落原创,更多内容请访问http://www.sunbloger.com/

在CentOS环境为PHP安装Memcached扩展

首先,安装PHP的Memcached扩展前,要先安装其所依赖的libmemcached,方法如下:

# wget https://launchpad.net/libmemcached/1.0/1.0.18/+download/libmemcached-1.0.18.tar.gz
# tar zxvf ./libmemcached-1.0.18.tar.gz
# cd libmemcached-1.0.18
# ./configure --prefix=/usr/local
# make
# make install

 

libmemcached安装完毕后,就可以开始安装Memcached扩展了,方法如下:

# wget https://pecl.php.net/get/memcached-2.2.0.tgz
# tar zxvf ./memcached-2.2.0.tgz
# cd memcached-2.2.0

 

解压缩后,我们需要先修改一下php_libmemcached_compat.h文件
将#include 的路径修改成#include </usr/local/include/libmemcached/memcached.h>然后再继续编译安装

# /usr/local/php/bin/phpize
# ./configure --with-php-config=/usr/local/php/bin/php-config --disable-memcached-sasl
# make
# make install

 

最后,还要修改php.ini文件,加入extension=memcached.so并重启php-fpm即可。

阳光部落原创,更多内容请访问http://www.sunbloger.com/

用 MiniFramework 快速构建 REST 风格的 API 接口

MiniFramework 是一款遵循 Apache2 开源协议发布的,支持 MVC 和 RESTful 的超轻量级 PHP 开发框架。

通过 MiniFramework 内置的 REST 接口功能,我们可以很轻松的快速构建起基于 REST 风格的 API 接口,特别是在开发 iOS 和 Android 手机客户端应用时,服务器端的 API 接口是否灵活高效,直接影响着手机应用的体验。

下面介绍一下如何使用 MiniFramework 开发 REST 风格的 API 接口。

第一步,我们下载最新 MiniFramework 1.0.2 版本

下载地址是:https://github.com/jasonweicn/MiniFramework/archive/1.0.2.zip

下载并解压缩后,会看到里面有 App 和 MiniFramework 两个目录,App 目录是一个附带的应用 demo,MiniFramework 目录是框架核心文件。

第二步,我们在 Apache 或 Nginx 中新建一个站点,并将站点的根目录指向 App/Public 这个目录。

设置好站点根目录后,我们可以测试一下,用浏览器访问下面的 URL 地址:

http://你的域名/index.php?c=index&a=index

如果可以显示“Hello World!”,说明站点已经部署成功了。

第三步,为了优化访问 URL 访问的便捷性,我们要给站点设置伪静态规则。

如果你用的是 Apache,那么附带的应用 demo 中已经提供了 .htaccess 文件,不需要额外的设置了。

如果你用的是 Nginx,那么需要在 nginx.conf 中,向对应站点的 server{} 段中,增加下面的代码:

location / {
    index  index.html index.php;
    if (!-e $request_filename) {
        rewrite ^/(.*)$ /index.php last;
    }
}

 

保存后,别忘记重启 Nginx 让配置生效。

经过上述配置后,用浏览器访问下面的 URL 地址:

http://你的域名/index/index

如果可以显示“Hello World!”,那就说明伪静态也配置成功了。

第四步,创建 API 程序

找到 App/Api 目录,这里是存放 API 接口的地方,在里面已经附带了一个名为 Version.php 的 demo,你可以参考这个文件的代码,编写自己的 API,比如我们创建一个名为 User.php,里面放置 get、post、put 和 delete 四个方法,分别对应 REST 中的 GET、POST、PUT 和 DELETE 请求。代码如下:

<?php
//首先要声明当前文件的命名空间为 App\Api
namespace App\Api;
 
//还要引入 Mini\Rest
use Mini\Rest;
 
class User extends Rest //必须要继承Rest类
{
    /**
     * 初始化
     */
    function _init()
    {
        //do something...
    }
    
    /**
     * GET
     */
    function get()
    {
        //我们临时构建一个用户列表数组,在你的业务代码中或许应该通过模型从数据库中读取
        $userlist = array(
            array('id'=>1, 'name'=>'user1'),
            array('id'=>2, 'name'=>'user2'),
            array('id'=>2, 'name'=>'user3')
        );
        
        //将$userlist通过responseJson()方法输出为JSON
        $this->responseJson(200, 'success', $userlist);
    }
    
    /**
     * POST
     */
    function post()
    {
        //获取POST参数
        $params = $this->params->getParams();
        
        //do something...
    }
    
    /**
     * PUT
     */
    function put()
    {
        //获取PUT参数(POST和PUT参数均可通过此方法获得)
        $params = $this->params->getParams();
        
        //do something...
    }
    
    /**
     * DELETE
     */
    function delete()
    {
        //返回HTTP状态码403(在REST中表示对于拒绝访问)
        $this->responseJson(403);
    }
}

 

创建好上边的 API 后,我们可以测试一下,用浏览器访问下面的 URL 地址:

http://你的域名/api/user

此时的访问请求属于 GET 方式,MiniFramework 会将这个请求映射到我们刚刚创建的 User 类的 get() 方法上,如果一切正常,我们会看到浏览器中显示如下内容:

{"code":200,"msg":"success","data":[{"id":1,"name":"user1"},{"id":2,"name":"user2"},{"id":2,"name":"user3"}]}

 

上边显示的内容就是通过 responseJson() 方法输出的 JSON 字符串了,其中 code 代表这次请求服务器返回的状态代码,msg 是返回的说明,data 里面就是这次请求发出后,服务器返回给客户端的数据了。

我们可以看到,上边 User 类的代码中,在最开始要通过 namespace 来声明当前文件的命名空间,在 MiniFramework 中,默认情况下 API 接口的命名空间统一为 App/Api。

再往下还要通过 use 引入 Mini\Rest,这个是 MiniFramework 的核心类之一,我们创建的 API 接口的 class 必须要继承 Rest。

再往下就是 REST 中经典的 get、post、put 和 delete 四个方法,对于客户端请求类型的映射问题,MiniFramework 会自动帮我们处理好,我们只要专注写好业务逻辑就可以了。

阳光部落原创,更多内容请访问 http://www.sunbloger.com/

书籍制作工具 GITBOOK 的安装方法

GitBook 是一个命令行工具(也是 Node.js 库),让你能够使用 GitHub/Git 和 Markdown 构建出美丽的书籍,可以包含互动的练习。GitBook 支持使用多种语言构建书籍。

GitBook支持输出多种文档格式,如:

静态站点:GitBook默认输出该种格式,生成的静态站点可直接托管搭载Github Pages服务上;
PDF:需要安装gitbook-pdf依赖;
eBook:需要安装ebook-convert;
单HTML网页:支持将内容输出为单页的HTML,不过一般用在将电子书格式转换为PDF或eBook的中间过程;
JSON:一般用于电子书的调试或元数据提取。

GitBook项目官网:http://www.gitbook.io
GitBook Github地址:https://github.com/GitbookIO/gitbook

基本安装

1、Node.js安装
Node.js 是一个基于Chrome JavaScript 运行时建立的一个平台, 用来方便地搭建快速的, 易于扩展的网络应用。Node.js 借助事件驱动, 非阻塞 I/O 模型变得轻量和高效, 非常适合 run across distributed devices 的 data-intensive的实时应用。

登录Node.js官网http://www.nodejs.org/,下载安装包并安装。

安装完成这后,你可以在终端模式下检验一下:

$ node -v
v0.10.29
看到些提示,就表示你已成功安装上了Node.js。

2、Gitbook安装
Gitbook是从NMP安装的,命令行:

$ npm install gitbook -g
安装完之后,你可以检验下是否安装成功:

$ gitbook -V
0.4.2
如果你看到了与上面类似的版本信息,则表示你已成功完装上了Gitbook。

3、calibre安装
Calibre是一个开源的“一站式”的电子书解决方案,它可以全面满足你的电子书需求。Calibre是免费的,源代码开放,拥有跨平台的设计。

Gitbook会使用其中的ebook-convert功能组件来完成书籍格式的转换。

登录calibre官网http://www.calibre-ebook.com/,下载安装。

至此,书籍制作工具GitBook安装完毕。

原文地址:http://blog.liyibo.org/books-installation-authoring-tool-gitbook/

SVN版本库迁移服务器方法

首先,在旧服务器上导出所有版本库

svnadmin dump /var/svn/project > /var/svn/project.dump

 

然后,将导出的 dump 文件拷贝到新服务器上,并在新服务器上创建同名的版本库

svnadmin create project

 

用 load 命令将 dump 文件还原到新服务器上的同名版本库里

svnadmin load project < project.dump

 

最后,别忘记参照旧服务器,去设置新服务器的 authz 和 serve.conf 等设置

阳光部落原创,更多内容请访问 http://www.sunbloger.com/

解决Cacti监控大内存时数据显示nan的问题

通过 Cacti 监控服务器内存使用情况时,Memory Usage 图表中,可能会出现 Cache Memory 或其他数据的值显示为 nan 的情况。出现这种情况大多是由于服务器内存较大,超出了 Cacti 数据模板中 10G 的预设上限值,我们可以通过修改此预设值来解决这个问题,下面是具体修改方法。

首先,登录 Cacti 后,进入到 Console > Data Templates 中,找到和内存监控相关的三个模板,分别是:“ucd/net – Memory – Buffers”、“ucd/net – Memory – Cache”和“ucd/net – Memory – Free”。

然后,逐一修改三个这三个模板中的“Maximum Value”,将这个值扩大至1000000000(100G)。

最后,在修改完模板后,还需要在 Cacti 中将 Memory Usage 相关的图表和数据源(Data Sources)删除重新创建,重建后稍等片刻,待下一次数据抓取后,就会看到原本显示 nan 地方现在都可以正常显示内存数据了。

阳光部落原创,更多内容请访问 http://www.sunbloger.com/

用PHP从本地提取视频并向浏览器输出的方法

有时,在一些特殊场景中,我们需要访问视频时,需要预先通过PHP做一些校验,校验通过后,才允许将视频数据输出给浏览器。

下面这段代码实现了用PHP从本地提取视频文件,并通过header函数以字节的方式向浏览器输出视频数据流。

<?php

//需要下载的文件
$file_name = 'test.mp4';

//下载文件必须先要将文件打开,写入内存
$fp = fopen($file_name, 'r+');

//判断文件是否存在
if (!file_exists($file_name)) {
    echo "文件不存在";
    exit();
}

//判断文件大小
$file_size = filesize($file_name);

//返回的文件
header('Content-type: application/octet-stream');

//按照字节格式返回
header('Accept-Ranges: bytes');

//返回文件大小
header('Accept-Length: ' . $file_size);

//弹出客户端对话框,对应的文件名
header('Content-Disposition: attachment; filename=' . $file_name);

//防止服务器瞬时压力增大,分段读取
$buffer = 4096;

while(!feof($fp)) {
    $file_data = fread($fp, $buffer);
    echo $file_data;
}

//关闭文件
fclose($fp);

?>

为CentOS升级OpenSSL 让Nginx支持TLS 1.2

最近在调试微信小程序时,发现wx.request请求总是无法正确获取服务器端的数据,经过检查发现是因为服务器端https不支持微信要求的TLS 1.2版本。

登录到服务器上,用openssl version -a命令查询,发现版本是0.9.8e,查阅文档得知OpenSSL从1.0.1开始才支持TLS 1.2,那么我们就来对OpenSSL进行个升级。

准备工作:
1.下载新版OpenSSL源码包https://www.openssl.org/source/openssl-1.0.1u.tar.gz
2.开启主机的telnet,以防升级过程中遇到问题,可通过telnet补救。

阅读更多