XAMPP for OS X 8.2.4 安装 sodium扩展

1、安装libsodium库
libsodium是sodium扩展的依赖库,您需要先安装它。在Mac上,您可以使用Homebrew来安装libsodium:

brew install libsodium

2、安装sodium扩展

首先下载PHP源码,https://www.php.net/distributions/php-8.2.4.tar.gz(可选择对应版本);然后解压,进入ext下sodium目录;

使用phpize命令准备编译环境(确保您的phpize与XAMPP中的PHP版本相匹配)。
运行./configure脚本配置扩展。
使用make和sudo make install命令编译并安装扩展。
在php.ini文件中添加extension=sodium.so(在Windows上可能是extension=php_sodium.dll)来启用扩展。

完整命令如下:

/Applications/XAMPP/bin/phpize

./configure --with-php-config=/Applications/XAMPP/bin/php-config

make

sudo make install

PS:确保Mac已安装autoconf(如无,需先安装:brew install autoconf)


Memcached 超时时间

Memcached 存储命令 expire 过期时间设置

问题:

拿set命令为例

bool Memcache::set ( string $key , mixed $var [, int $flag [, int $expire ]] )

一个同事将 $expire 设置为100天,发现设置的key总是获取不到值…

 

 

因:

一些存储命令在发送时会包含一个失效值(与一个元素或一个客户端操作请求相关)到服务端。所有这类用法,实际发送的值可以 是一个Unix时间戳(自1970年1月1日起至失效时间的整型秒数),或者是一个从现在算起的以秒为单位的数字。对于后一种情况,这个 秒数不能超过60×60×24×30(30天时间的秒数);如果失效的值大于这个值, 服务端会将其作为一个真实的Unix时间戳来处理而不是 自当前时间的偏移。

如果失效值被设置为0(默认),此元素永不过期(但是它可能由于服务端为了给其他新的元素分配空间而被删除)

 

 

Memcache::set

(PECL memcache >= 0.2.0)

Memcache::set — Store data at the server

说明

bool Memcache::set ( string $key , mixed $var [, int $flag [, int $expire ]] )

Memcache::set()key存储一个元素值为 var。参数expire是以秒为单位的失效时间, 如果设置为0表明该元素永不过期(但是它可能会因为为了给其他项分配空间而被删除)。如果你希望存储的元素 经过压缩(使用zlib),你可以设置flag的值为MEMCACHE_COMPRESSED

Note:

谨记:资源类型变量(比如文件或连接)不能被存储在缓存中,因为它们在序列化状态不能被完整描述。

 

同样你也可以使用函数memcache_set()。 

参数

 

key
要设置值的key。

var
要存储的值,字符串和数值直接存储,其他类型序列化后存储。

flag
使用MEMCACHE_COMPRESSED指定对值进行压缩(使用zlib)。

expire
当前写入缓存的数据的失效时间。如果此值设置为0表明此数据永不过期。你可以设置一个UNIX时间戳或 以秒为单位的整数(从当前算起的时间差)来说明此数据的过期时间,但是在后一种设置方式中,不能超过 2592000秒(30天)。

 

返回值

成功时返回 TRUE, 或者在失败时返回 FALSE

范例

 

Example #1 Memcache::set() 示例

<?php
/* procedural API */

/* connect to memcached server */
$memcache_obj = memcache_connect('memcache_host', 11211);

/*
设置'var_key'对应存储的值
flag参数使用0,值没有经过压缩
失效时间为30秒
*/
memcache_set($memcache_obj, 'var_key', 'some variable', 0, 30);

echo memcache_get($memcache_obj, 'var_key');

?>

Example #2 Memcache::set() 示例

<?php
/* OO API */

$memcache_obj = new Memcache;

/* connect to memcached server */
$memcache_obj->connect('memcache_host', 11211);

/*
设置'var_key'对应值,使用即时压缩
失效时间为50秒
*/
$memcache_obj->set('var_key', 'some really big variable', MEMCACHE_COMPRESSED, 50);

echo $memcache_obj->get('var_key');

?>

 


排列组合

//$words = array(‘china’,’mother’,’father’,’hello’,’welcome’);

//排列组合

$words = array(‘a’, ‘b’, ‘c’, ‘d’, ‘e’);
$res = array();
getCombines($words, 5);
print_r($res);
function getCombines($arr, $len=0, $str=””) {
global $res;
$arr_len = count($arr);
if($len == 0){
$res[] = $str;
}else{
for($i=0; $i<$arr_len; $i++){
$tmp = array_shift($arr);
if (empty($str))
{
getCombines($arr, $len-1, $tmp);
}
else
{
getCombines($arr, $len-1, $str.”,”.$tmp);
}
array_push($arr, $tmp);
}
}
}


PHP中将字符串转化为整数(int) intval() printf()

背景、概述
  早在Sql注入横行的前几年,字符串转化为整数就已经被列为每个web程序必备的操作了。web程序将get或post来的id、整数等值强制经过转化函数转化为整数,过滤掉危险字符,尽可能降低系统本身被Sql注入的可能性。
现如今,虽然Sql注入已经逐渐淡出历史舞台,但是,为了保证web程序的正常运行,减少出错概率,更好的保证用的满意度,我们同样需要将用户的不正确输入转化为我们所需要的。
转化方式
在PHP中,我们可以使用3种方式将字符串转化为整数。
1.强制类型转换方式
  强制类型转换方式,就是“在要转换的变量之前加上用括号括起来的目标类型”(摘自PHP手册“类型戏法”节)的方式。

代码如下:

<?php
$foo = “1”; // $foo 是字符串类型
$bar = (int)$foo; // $bar 是整型
?>

对于整型来说,强制转换类型名称为int或者integer。
2.内置函数方式
  内置函数方式,就是使用PHP的内置函数intval进行变量的转换操作。

代码如下:
<?php
$foo = “1”; // $foo 是字符串类型
$bar = intval($foo); // $bar 是整型
?>

intval函数的格式为:
  int intval(mixed $var [, int $base]); (摘自PHP手册)
虽然PHP手册中明确指出,intval()不能用于array和object的转换。但是经过我测试,转换array的时候不会出任何问题,转换值为1,而不是想象中的0。恐怕是因为在PHP内部,array类型的变量也被认为是非零值得缘故吧。转换object的时候,PHP会给出如下的 notice:
Object of class xxxx could not be converted to int in xxxxx.php on line xx
转换值同样为1。
3.格式化字符串方式
格式化字符串方式,是利用sprintf的%d格式化指定的变量,以达到类型转换的目的。

代码如下:
<?php
$foo = “1”; // $foo 是字符串类型
$bar = sprintf(“%d”, $foo); // $bar 是字符串类型
?>

严格意义上讲sprintf的转换结果还是string型,因此它不应该算是字符串转化为整数的方式。但是经过他处理之后的字符串值确实已经成为了“被强制转化为字符串类型的整数”。
实际测试
上面介绍了PHP中,将字符串转化为整数的3种方式。对于一般的程序员来说,看到这里就算结束了,下面的部分是针对变态程序员的。
1.基本功能测试
  设定以下数组:

代码如下:
<?php
$a[] = “1”;
$a[] = “a1”;
$a[] = “1a”;
$a[] = “1a2”;
$a[] = “0”;
$a[] = array(‘4’,2);
$a[] = “2.3”;
$a[] = “-1”;
$a[] = new Directory();
?>

使用三种方式依次转化上面给出的数组中的元素,查看转换情况。程序源代码如下:

代码如下:
<?php
$a[] = “1”;
$a[] = “a1”;
$a[] = “1a”;
$a[] = “1a2”;
$a[] = “0”;
$a[] = array(‘4’,2);
$a[] = “2.3”;
$a[] = “-1”;
$a[] = new Directory();
// int
print “(int)<br />”;
foreach($a as $v)
{
var_dump((int)$v);
print “<br />”;
}
// intval
print “intval();<br />”;
foreach($a as $v)
{
var_dump(intval($v));
print “<br />”;
}
// sprintf
print “sprintf();<br />”;
foreach($a as $v)
{
var_dump(sprintf(“%d”, $v));
print “<br />”;
}
?>

程序的最终运行结果如下(已经去掉转换object时出现的notice):
(int)
int(1)
int(0)
int(1)
int(1)
int(0)
int(1)
int(2)
int(-1)
int(1)
intval();
int(1)
int(0)
int(1)
int(1)
int(0)
int(1)
int(2)
int(-1)
int(1)
sprintf();
string(1) “1”
string(1) “0”
string(1) “1”
string(1) “1”
string(1) “0”
string(1) “1”
string(1) “2”
string(2) “-1”
string(1) “1”
由此可以看出,三种转换的结果是完全一样的。那么从功能上讲,3种方式都可以胜任转换工作,那么接下来的工作就是看哪一种效率更高了。
2.性能测试
被测试字符串是我们在注入工作中可能会使用到的一种:

复制代码代码如下:
<?php
$foo = “1′;Select * …”;
?>
获取时间点的函数如下(用于获取测试起始点和结束点,以计算消耗时间):

<?php
**
* Simple function to replicate PHP 5 behaviour
*/
function microtime_float()
{
list($usec, $sec) = explode(” “, microtime());
return ((float)$usec + (float)$sec);
}
?>

(摘自PHP手册microtime()函数节)
测试过程是使用每种方式转换变量$foo 1000000次(100万次),并将各自的消耗时间输出,总共进行三组测试,尽可能降低误差。测试程序如下:

复制代码代码如下:
<?php
function microtime_float()
{
list($usec, $sec) = explode(” “, microtime());
return ((float)$usec + (float)$sec);
}
$foo = “1′;Select * …”;

// (int)
$fStart = microtime_float();
for($i=0;$i<1000000;$i++)
{
$bar = (int)$foo;
}
$fEnd = microtime_float();
print “(int):” . ($fEnd – $fStart) . “s<br />”;
// intval()
$fStart = microtime_float();
for($i=0;$i<1000000;$i++)
{
$bar = intval($foo);
}
$fEnd = microtime_float();
print “intval():” . ($fEnd – $fStart) . “s<br />”;
// sprintf()
$fStart = microtime_float();
for($i=0;$i<1000000;$i++)
{
$bar = sprintf(“%d”, $foo);
}
$fEnd = microtime_float();
print “sprintf():” . ($fEnd – $fStart) . “s<br />”;
?>

最终的测试结果:
(int):0.67205619812012s
intval():1.1603000164032s
sprintf():2.1068270206451s
(int):0.66051411628723s
intval():1.1493890285492s
sprintf():2.1008238792419s
(int):0.66878795623779s
intval():1.1613430976868s
sprintf():2.0976209640503s

虽然这个测试有点变态(谁会连续转换100w次的整数?),但是由此可以看出,使用强制类型转换将字符串转化为整数速度是最快的。
总结
使用强制类型转换方式将字符串转化为整数是最直接的转化方式之一(可以直接获得整型的变量值)。从代码可读性角度上讲,sprintf方式代码比较长,而且其结果有可能还需要再次进行强制类型转换,而intval函数是典型的面向过程式转换,强制类型转换则比较直接的将“我要转化”这个思想传递给阅读者。从效率上讲,强制类型转换方式也是最快速的转化方式。因此,对于经常进行转化工作的程序员,我推荐使用这种方式。


php 常量定义 const与define的区别

在php中定义常量时,可用到const与define这两种方法,那他们到底有什么区别呢?

1.const用于类成员变量的定义,一经定义,不可修改。define不可用于类成员变量的定义,可用于全局常量。

2.const可在类中使用,define不能。

3.const不能在条件语句中定义常量。

如:if(constition){

哲理不能用const,只能用define

}

4.const只能接受静态的标量,而define可采用任何的表达式。

const BIT_5 = 1 << 5;    // invalid
define(‘BIT_5’, 1 << 5); // valid

5.const定义的常量时大小写敏感的,而define可通过第三个参数(为true表示大小写不敏感)来指定大小写是否敏感。

6.const采用一个普通的常量名称。而define可采用表达式作为常量。

7.使用const使得代码简单易读,const本身就是一个语言结构。而define是一个函数。

8.const在编译时比define快很多。


ThinkPHP3.2.2中自定义函数的一些方法

thinkphp中自定义函数的使用方法:

一、将函数放置于系统目录:ThinkPHP/Common/function.php 下,可直接调用;

二、将自定义函数旋转于系统目录扩展函数文件:ThinkPHP/Common/extend.php下,调用时需要加载:LOAD(‘extend’),一般不用这个,直接复制到项目下用第三种方法直接调用;

三、将自定义函数放置于项目函数:AppPath/Common/Common/function.php(若没有该文件,需新建)下,也可以直接调用,在控制器和MODEL类中都可以。

四、将自定义函数放置于项目函数:AppPath/AppName/Common/function.php(若没有该文件,需新建)下,也可以直接调用,在该AppName的控制器和MODEL类中都可以。

 

建议使用第三、四种方式,尽量不要去修改ThinkPHP框架中的文件,避免在升级时,造成不必要的麻烦~


PHP usleep() 函数

定义和用法

usleep() 函数延迟代码执行若干微秒。

语法

usleep(microseconds)
参数 描述
microseconds 必需。以微秒计的暂停时间。

返回值

无返回值。

提示和注释

注释:在 PHP 5 之前,该函数无法工作于 Windows 系统上。

注释:一微秒等于百万分之一秒。

例子

<?php
echo date('h:i:s') . "<br />";

//延迟 10 描述
usleep(10000000);

//再次开始
echo date('h:i:s');
?>

输出:

09:23:14
09:23:24

相关函数推荐:php sleep()函数


PHP sleep() 函数

定义和用法

sleep() 函数延迟代码执行若干秒。

语法

sleep(seconds)
参数 描述
seconds 必需。以秒计的暂停时间。

返回值

若成功,返回 0,否则返回 false。

错误/异常

如果指定的描述 seconds 是负数,该函数将生成一个 E_WARNING。

例子

<?php
echo date('h:i:s') . "<br />";

//暂停 10 秒
sleep(10);

//重新开始
echo date('h:i:s');

?>

输出:

12:00:08
12:00:18

相关函数推荐:php usleep()函数