本文目录一览:
- 效率为王 分享几个提升php运行效率的代码规
- PHP代码修改
- 关于PHP的问题
- 什么是psr-0,psr-1,psr-2标准
- 高质量PHP代码的50个技巧(3)
- 今天说一下php多人开发大项目时如何做到代码规范化
效率为王 分享几个提升php运行效率的代码规
- 尽量静态化: 之所以强调静态化,是因为静态化后网站的访问速度可以提升1/4以上,内容越多,这个提升的效果越明显。 其实静态方法和非静态方法的效率主要区别在内存:静态方法在程序开始时生成内存,实例方法在程序运行中生成内存,所以静态方法可以直接调用,实例方法要先生成实例,通过实例调用方法,静态速度很快,但是多了会占内存。 任何语言都是对内存和磁盘的操作,至于是否面向对象,只是软件层的问题,底层都是一样的,只是实现方法不同。静态内存是连续的,因为是在程序开始时就生成了,而实例申请的是离散的空间,所以当然没有静态方法快。 静态方法始终调用同一块内存,其缺点就是不能自动进行销毁,而是实例化可以销毁。
- echo的效率高于print,因为
echo
没有返回值,print
返回一个整型;并且使用echo
的多重参数(译注:指用逗号而不是句点)代替字符串连接,比如echo $str1, $str2
。 测试:echo
:0.000929 - 0.001255 s(平均 0.001092 秒)print
:0.000980 - 0.001396 秒(平均 0.001188 秒) 相差8%左右,总体上echo
是比较快的。 注意,echo
大字符串的时候,如果没有做调整就严重影响性能。使用打开 Apache 的mod_deflate
进行压缩或者打开ob_start
先将内容放进缓冲区。
- 在循环之前设置循环的最大次数,而非在循环中。
- 如果能将类的方法定义成
static
,就尽量定义成static
,它的速度会提升将近4倍。 - 销毁变量去释放内存,特别是大的数组。 数组和对象在 PHP 特别占内存的,这个由于 PHP 的底层的 Zend 引擎引起的。 一般来说,PHP 数组的内存利用率只有 1/10,也就是说,一个在 C 语言里面 100M 内存的数组,在 PHP 里面就要 1G。 特别是在 PHP 作为后台服务器的系统中,经常会出现内存耗费太大的问题。
PHP代码修改
请确保你有“text.ttf”这个文件,你的程序用到了这个文件,不然还会报错。 下面是我改好的代码:
<?php if (!isset($_FILES['upfile'])): ?>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=gb2312" />
<title>wnh3的改造</title>
</head>
<body>
<form action="" enctype="multipart/form-data" method="post" name="upform">
上传文件:
<input name="upfile" type="file" />
<input type="submit" value="上传" /><br />
</form>
</body>
</html>
<?php else: ?>
<?php
if (is_uploaded_file($_FILES['upfile']['tmp_name'])) {
$upfile = $_FILES["upfile"];
$name = $upfile["name"];
$type = $upfile["type"];
$size = $upfile["size"];
$tmp_name = $upfile["tmp_name"];
$error = $upfile["error"];
switch ($type) {
case 'image/pjpeg':
$ok = 1;
break;
case 'image/jpeg':
$ok = 1;
break;
case 'image/gif':
$ok = 1;
break;
case 'image/png':
$ok = 1;
break;
}
}
$img = getimagesize($tmp_name);
switch ($img[2]) {
case 1:
$img = @imagecreatefromGIF($tmp_name);
break;
case 2:
$img = @imagecreatefromJPEG($tmp_name);
break;
case 3:
$img = @imagecreatefromPNG($tmp_name);
break;
}
$te = @imagecolorallocate($img, 255, 255, 255);
$str = iconv("GBK", "UTF-8", "我会登上世界的巅峰,成为你们仰视的存在");
imagettftext($img, 12, 0, 20, 20, $te, 'text.ttf', $str);
imagejpeg($img, "11.jpg");
?>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=gb2312" />
<title>wnh3的改造</title>
</head>
<body>
<h1>上传成功</h1>
</body>
</html>
<?php endif; ?>
关于PHP的问题
检查过,感觉没什么问题,就是变量传递的问题。 按理说,其他两个值能取到,中间这一个不会有问题的。 试处理方法:
- 你先检查一下拼写,有没有编码方面的问题(英文字符结果打成了全角的,比如
'
和’
等等); - 拼写无误的话,你试着把中间的变量名改一下,HTML 里面的名称和 PHP 文件里的名称尽量用不同的;
- 以上都没有问题的话,看看你的 Apache 环境的设置上有没有问题吧;
- 有时候程序是会出一些稀奇古怪的问题,别着急。也有可能是在传递的过程中数据丢失造成的,POST 过来的时候出了问题。打印一下
$_POST["oilqty"]
试试; - 提一点小建议:写代码要规范一点,该用
"
就用"
,不要省事,这样以后改动和检查时都很方便,层次分明。
什么是psr-0,psr-1,psr-2标准
转自: FIG 组织在制定跟 PHP 相关规范,简称 PSR,PSR 旨在通过讨论我们代码项目的共同点以找出一个协作编程的方法。
什么是 PSR-0(强调自动加载的方式)
下文描述了若要使用一个通用的自动加载器(autoloader),你所需要遵守的规范:
规范
一个完全标准的命名空间(namespace)和类(class)的结构是这样的:\*
- 每个命名空间(namespace)都必须有一个顶级的空间名(namespace)("组织名(Vendor Name)")。
- 每个命名空间(namespace)中可以根据需要使用任意数量的子命名空间(sub-namespace)。
- 从文件系统中加载源文件时,空间名(namespace)中的分隔符将被转换为
DIRECTORY_SEPARATOR
。 - 类名(class name)中的每个下划线
_
都将被转换为一个DIRECTORY_SEPARATOR
。下划线_
在空间名(namespace)中没有什么特殊的意义。 - 完全标准的命名空间(namespace)和类(class)从文件系统加载源文件时将会加上
.php
后缀。 - 组织名(vendor name),空间名(namespace),类名(class name)都由大小写字母组合而成。
示例
\Doctrine\Common\IsolatedClassLoader
→/path/to/project/lib/vendor/Doctrine/Common/IsolatedClassLoader.php
\Symfony\Core\Request
→/path/to/project/lib/vendor/Symfony/Core/Request.php
\Zend\Acl
→/path/to/project/lib/vendor/Zend/Acl.php
\Zend\Mail\Message
→/path/to/project/lib/vendor/Zend/Mail/Message.php
空间名(namespace)和类名(class name)中的下划线
\namespace\package\Class_Name
→/path/to/project/lib/vendor/namespace/package/Class/Name.php
\namespace\package_name\Class_Name
→/path/to/project/lib/vendor/namespace/package_name/Class/Name.php
以上是我们为实现通用的自动加载而制定的最低标准。你可以利用能够自动加载 PHP 5.3 类的SplClassLoader
来测试你的代码是否符合这些标准。
实例
下面是一个怎样利用上述标准来实现自动加载的示例函数:
<?php
function autoload($className)
{
$className = ltrim($className, '\\');
$fileName = '';
$namespace = '';
if ($lastNsPos = strrpos($className, '\\')) {
$namespace = substr($className, 0, $lastNsPos);
$className = substr($className, $lastNsPos + 1);
$fileName = str_replace('\\', DIRECTORY_SEPARATOR, $namespace) . DIRECTORY_SEPARATOR;
}
$fileName .= str_replace('_', DIRECTORY_SEPARATOR, $className) . '.php';
require $fileName;
}
SplClassLoader 实现
下面的 gist 是一个按照上面建议的标准来自动加载类的 SplClassLoader
实例。这是依据这些标准来加载 PHP 5.3 类的推荐方案。
什么是 PSR-1(定义基本代码规范)
本节我们将会讨论一些基本的代码规范问题,以此作为将来讨论更高级别的代码分享和技术互用的基础。
1. 概述
- 源文件必须只使用
<?php
和<?=
这两种标签。 - 源文件中 PHP 代码的编码格式必须只使用不带字节顺序标记(BOM)的 UTF-8。
- 一个源文件建议只用来做声明(类(class),函数(function),常量(constant)等)或者只用来做一些引起副作用的操作(例如:输出信息,修改.ini配置等),但不建议同时做这两件事。
- 命名空间(namespace)和类(class)必须遵守 PSR-0 标准。
- 类名(class name)必须使用骆驼式(StudlyCaps)写法。
- 类(class)中的常量必须只由大写字母和下划线(_)组成。
- 方法名(method name)必须使用驼峰式(camelCase)写法。
2. 文件
2.1. PHP 标签
PHP 代码必须只使用长标签(<?php ... ?>
)或者短输出式标签(<?= ... ?>
);而不可使用其他标签。
2.2. 字符编码
PHP 代码的编码格式必须只使用不带字节顺序标记(BOM)的 UTF-8。
2.3. 副作用
一个源文件建议只用来做声明(类(class),函数(function),常量(constant)等)或者只用来做一些引起副作用的操作(例如:输出信息,修改.ini配置等),但不建议同时做这两件事。
“副作用”(side effects)的意思是:在包含文件时所执行的逻辑与所声明的类(class)、函数(function)、常量(constant)等没有直接的关系。
副作用包含但不局限于:产生输出,显式地使用 require
或 include
,连接外部服务,修改 ini 配置,触发错误或异常,修改全局或者静态变量,读取或修改文件等等。
下面是一个既包含声明又有副作用的示例文件;即应避免的例子:
<?php
// 副作用:修改了 ini 配置
ini_set('error_reporting', E_ALL);
// 副作用:载入了文件
include "file.php";
// 副作用:产生了输出
echo "<html>\n";
// 声明
function foo()
{
// 函数体
}
下面是一个仅包含声明的示例文件;即应提倡的例子:
<?php
// 声明
function foo()
{
// 函数体
}
// 条件式声明不算做是副作用
if (!function_exists('bar')) {
function bar()
{
// 函数体
}
}
3. 空间名(namespace)和类名(class name)
命名空间(namespace)和类(class)必须遵守 PSR-0。 这意味着一个源文件中只能有一个类(class),并且每个类(class)至少要有一级空间名(namespace):即一个顶级的组织名(vendor name)。 类名(class name)必须使用 StudlyCaps 写法。 PHP 5.3 之后的代码必须使用正式的命名空间(namespace):
<?php
// PHP 5.3 及之后:
namespace Vendor\Model;
class Foo
{
}
PHP 5.2.x 之前的代码建议用伪命名空间 Vendor_
作为类名(class name)的前缀:
<?php
// PHP 5.2.x 及之前:
class Vendor_Model_Foo
{
}
4. 类的常量、属性和方法
术语“类”(class)指所有的类(class)、接口(interface)和特性(trait)。
4.1. 常量
类常量必须只由大写字母和下划线(_)组成。例如:
<?php
namespace Vendor\Model;
class Foo
{
const VERSION = '1.0';
const DATE_APPROVED = '2012-06-01';
}
4.2. 属性
本指南中故意不对 $StulyCaps
、$camelCase
或者 $unser_score
中的某一种风格作特别推荐,完全由读者依据个人喜好决定属性名的命名风格。
但是不管你如何定义属性名,建议在一个合理的范围内保持一致。这个范围可能是组织(vendor)级别的,包(package)级别的,类(class)级别的,或者方法(method)级别的。
4.3. 方法
方法名则必须使用 camelCase 风格来声明。
什么是 PSR-2(定义代码风格)
代码风格指南 本手册是基础代码规范(PSR-1)的继承和扩展。 为了尽可能的提升阅读其他人代码时的效率,下面列举了一系列的通用规则,特别是有关于 PHP 代码风格的。 各个成员项目间的共性组成了这组代码规范。当开发者们在多个项目中合作时,本指南将会成为所有这些项目中共用的一组代码规范。因此,本指南的益处不在于这些规则本身,而在于在所有项目中共用这些规则。 RFC 2119 中的必须(MUST)、不可(MUST NOT)、建议(SHOULD)、不建议(SHOULD NOT)、可以/可能(MAY)等关键词将在本节用来做一些解释性的描述。
高质量PHP代码的50个技巧(3)
42
43
44
45
/**
* Method to execute a command in the terminal
* Uses:
* 1. system
* 2. passthru
* 3. exec
* 4. shell_exec
*/
function terminal($command)
{
// system
if (function_exists('system')) {
ob_start();
system($command, $return_var);
$output = ob_get_contents();
ob_end_clean();
}
// passthru
else if (function_exists('passthru')) {
ob_start();
passthru($command, $return_var);
$output = ob_get_contents();
ob_end_clean();
}
// exec
else if (function_exists('exec')) {
exec($command, $output, $return_var);
$output = implode("\n", $output);
}
// shell_exec
else if (function_exists('shell_exec')) {
$output = shell_exec($command);
}
else {
$output = 'Command execution not possible on this system';
$return_var = 1;
}
return array('output' => $output, 'status' => $return_var);
}
terminal('ls');
上面的函数将运行 shell 命令,只要有一个系统函数可用,这保持了代码的一致性。
5. 灵活编写函数
function add_to_cart($item_id, $qty)
{
$_SESSION['cart']['item_id'] = $qty;
}
add_to_cart('IPHONE3', 2);
使用上面的函数添加单个项目。而当添加项列表的时候,你要创建另一个函数吗?不用,只要稍加留意不同类型的参数,就会更灵活。例如:
function add_to_cart($item_id, $qty)
{
if (!is_array($item_id)) {
$_SESSION['cart']['item_id'] = $qty;
} else {
foreach ($item_id as $i_id => $qty) {
$_SESSION['cart'][$i_id] = $qty;
}
}
}
add_to_cart('IPHONE3', 2);
add_to_cart(array('IPHONE3' => 2, 'IPAD' => 5));
现在,同一个函数可以处理不同类型的输入参数了。可以参照上面的例子重构你的多处代码,使其更智能。
6. 有意忽略 PHP 关闭标签
我很想知道为什么这么多关于 PHP 建议的博客文章都没提到这点。
<?php
echo "Hello";
// Now don't close this tag
这将节约你很多时间。我们举个例子:
一个 super_class.php
文件:
<?php
class super_class
{
function super_function()
{
// super code
}
}
?>
// super extra character after the closing tag
index.php
:
<?php
require_once('super_class.php');
// echo an image or pdf, or set the cookies or session data
这样,你将会得到一个 Headers already send
错误。为什么?因为 “super extra character” 已经被输出了。现在你得开始调试啦。这会花费大量时间寻找 “super extra” 的位置。因此,养成省略关闭符的习惯:
<?php
class super_class
{
function super_function()
{
// super code
}
}
// No closing tag
这会更好。
7. 在某地方收集所有输入,一次输出给浏览器
这称为输出缓冲,假如说你已在不同的函数输出内容:
function print_header()
{
echo "<p id='header'>Site Log and Login links</p>";
}
function print_footer()
{
echo "<p id='footer'>Site was made by me</p>";
}
print_header();
for ($i = 0; $i < 100; $i++) {
echo "I is : $i <br />";
}
print_footer();
替代方案,在某地方集中收集输出。你可以存储在函数的局部变量中,也可以使用 ob_start
和 ob_end_clean
。例如:
function print_header()
{
$o = "<p id='header'>Site Log and Login links</p>";
return $o;
}
function print_footer()
{
$o = "<p id='footer'>Site was made by me</p>";
return $o;
}
echo print_header();
for ($i = 0; $i < 100; $i++) {
echo "I is : $i <br />";
}
echo print_footer();
为什么需要输出缓冲:
- 可以在发送给浏览器前更改输出。如
str_replace
函数或可能是preg_replace
或添加些监控/调试的 HTML 内容。 - 输出给浏览器的同时又做 PHP 的处理很糟糕。你应该看到过有些站点的侧边栏或中间出现错误信息。知道为什么会发生吗?因为处理和输出混合了。
8. 发送正确的 MIME 类型头信息,如果输出非 HTML 内容的话
输出一些 XML:
$xml = "<?xml version='1.0' encoding='utf-8' standalone='yes'?>";
$xml = "<response><code>0</code></response>";
// Send XML data
echo $xml;
工作得不错。但需要一些改进:
$xml = "<?xml version='1.0' encoding='utf-8' standalone='yes'?>";
$xml = "<response><code>0</code></response>";
header('Content-Type: application/xml');
echo $xml;
今天说一下php多人开发大项目时如何做到代码规范化
模块独立开发。写好接口,供他人消费。不是自己的模块不要插手。