关于 PHP 的数据类型 (二)

php数据类型-字符串
string (字符串):
一个字符串由一系列的字符组成,其中每个字符等同于一个字节。这意味着PHP只能支持 256 的字符集,因此不支持 Unicode;

string 类型最大可以达到 2GB;

字符串的三种表达方式:

  • 单引号
  • 双引号
  • heredocnowdoc

单引号:定义一个字符串的最简单的方法是用单引号把他包围起来(字符);

  • 单引号不能解析变量;
  • 单引号只能解析单引号和反斜线本身;
  • 变量与变量,变量与字符串之间,字符串与字符串之间使用 . 来连接;

双引号:定义一个字符串也可以使用双引号将它包围起来(字符);

  • 双引号可以解析变量,变量可以使用特殊字符和 {} 包含;
  • 双引号可以解析所有的转移字符;
  • 变量与变量,变量与字符串之间,字符串与字符串之间使用 . 来连接;

效率:单引号的效率要高于双引号;

双引号里的变量会经过编译器解释,然后在输出,单引号直接输出;

example1.php

//单引号实例
<?php
echo 'this is a simple string';

// 可以录入多行
echo 'You can also have embedded newlines in 
strings this way as it is
okay to do';

// 输出: Arnold once said: "I'll be back"
echo 'Arnold once said: "I\'ll be back"';

// 输出: You deleted C:\*.*?
echo 'You deleted C:\\*.*?';

// 输出: You deleted C:\*.*?
echo 'You deleted C:\*.*?';

// 输出: This will not expand: \n a newline
echo 'This will not expand: \n a newline';

// 输出: Variables do not $expand $either
echo 'Variables do not $expand $either';
?>

example2.php

<?php
//双引号实例
$a = 123;
$str = "abcd{$a}efg";  //双引号可以解析变量,使用 {} 将变量括起来。 {} 不会输出;
$str1 = 'abcd@$a@efg'; //可以使用特殊字符将变量括起来,但是特殊字符会输出  abcd@123@efg
$str2 = "abcd'$a'efg"; // 双引号中有单引号,此种情况变量可以被解析,同时单引号也会输出  abcd'123'efg;
?>

heredocnowdoc:
表达字符串的方法是用 heredoc 句法结构:<<< 在该运算符之后要提供一个标识符,然后换行。 接下来是字符串本身,最后要用前面定义的标识符作为结束标志。 结束时所引用的标识符 必须 在该行的第一列,而且,标识符的命名也要像其它标签一样遵守 PHP 的规则:只能包含字母、数字和下划线,并且必须以字母和下划线作为开头;

注意:要注意的是结束标识符这行除了可能有一个分号(;)外,绝对不能包含其它字符;
heredoc 类似于 双引号,字符串中 可以 解析变量,但是 不可以 转移字符;(就像没有使用双引号"" 的双引号字符串)

example3.php

<?php
$str = <<<EOD
Example of string
spanning multiple lines
using heredoc syntax.
EOD;

/* 含有变量的更复杂示例 */
class foo
{
    var $foo;
    var $bar;

    function foo()
    {
        $this->foo = 'Foo';
        $this->bar = array('Bar1', 'Bar2', 'Bar3');
    }
}

$foo = new foo();
$name = 'MyName';

echo <<<EOT
My name is "$name". I am printing some $foo->foo.
Now, I am printing some {$foo->bar[1]}.
This should print a capital 'A': \x41
EOT;
?>

以上会输出:
My name is "MyName". I am printing some Foo.
Now, I am printing some Bar2.
This should print a capital 'A': A

  • 可以把 heredoc 结构用在函数参数中来传递数据:
    <?php
    var_dump(array(<<<EOD
    foobar!
    EOD
    ));
    ?>
  • 可以用 heredoc 结构来初始化静态变量和类属性和常量:
<?php
// 静态变量
function foo()
{
    static $bar = <<<LABEL
Nothing in here...
LABEL;
}

// 类的常量、属性
class foo
{
    const BAR = <<<FOOBAR
Constant example
FOOBAR;

    public $baz = <<<FOOBAR
Property example
FOOBAR;
}
?>
  • 可以在 heredoc 结构中使用双引号来声明标识符:
    <?php
    echo <<<"FOOBAR"
    Hello World!
    FOOBAR;
    ?>

Nowdoc 结构:
Nowdoc 结构是类似于单引号字符串的。但是 nowdoc 中不进行解析操作;这种结构很适合用于嵌入 PHP 代码或其它大段文本而无需对其中的特殊字符进行转义;一个 nowdoc 结构也用和 heredocs 结构一样的标记 <<<, 但是跟在后面的标识符要用单引号括起来,即 <<<'EOT'。

example4.php

<?php
$str = <<<'EOD'
Example of string
spanning multiple lines
using nowdoc syntax.
EOD;

/* 含有变量的更复杂的示例 */
class foo
{
    public $foo;
    public $bar;

    function foo()
    {
        $this->foo = 'Foo';
        $this->bar = array('Bar1', 'Bar2', 'Bar3');
    }
}

$foo = new foo();
$name = 'MyName';

echo <<<'EOT'
My name is "$name". I am printing some $foo->foo.
Now, I am printing some {$foo->bar[1]}.
This should not print a capital 'A': \x41
EOT;
?>

以上会输出:
My name is "$name". I am printing some $foo->foo.
Now, I am printing some {$foo->bar[1]}.
This should not print a capital 'A': \x41

  • nowdoc 结构可以用在任意的静态数据环境中,最典型的示例是用来初始化类的属性或常量;

    <?php
    class foo {
    public $bar = <<<'EOT'
    bar
    EOT;
    }
    ?>
  • 变量解析:

    当字符串用 双引号heredoc 结构定义时,其中的变量将会被解析。

  • 存取和修改字符串中的字符:

    string 中的字符可以通过一个从 0 开始的下标,用类似 array 结构中的方括号包含对应的数字来访问和修改,比如 $str[42]。可以把 string 当成字符组成的 array;也可用 花括号 访问,比如 $str{42}

注意

  • 超出 字符串长度的下标写入将会 拉长该字符串以空格 填充。
  • 非整数 类型下标会被 转换成整数
  • 非法下标 类型会产生一个 E_NOTICE 级别错误。
  • 负数下标 写入字符串时会产生一个 E_NOTICE 级别错误,用 负数下标读取 字符串时返回 空字符串
  • 写入 时只用到了赋值字符串的 第一个 字符。
  • 空字符串赋值 则赋给的值是 NULL 字符。
  • 字符串 在内部是字节组成的数组。 因此用花括号访问或修改字符串对多字节字符集很 不安全 。仅应对单字节编码例如 ISO-8859-1 的字符串进行此类操作。

example5.php

<?php
// 取得字符串的第一个字符
$str = 'This is a test.';
$first = $str[0];

// 取得字符串的第三个字符
$third = $str[2];

// 取得字符串的最后一个字符
$str = 'This is still a test.';
$last = $str[strlen($str)-1]; 

// 修改字符串的最后一个字符
$str = 'Look at the sea';
$str[strlen($str)-1] = 'e';

?>

字符串下标 必须为整数可转换为整数的字符串,否则会发出 警告。之前类似 "foo" 的下标会无声地转换成 0

转换成字符串:

一个值可以通过在其前面加上 (string) 或者使用 strval() 函数来转变成字符串;

  • 一个布尔值 boolean 的 TRUE 被转换成 string 的 "1"Boolean 的 FALSE 被转换成 ""(空字符串)。这种转换可以在 boolean 和 string 之间相互进行。
  • 一个整数 integer 或浮点数 float 被转换为数字的字面样式的 string(包括 float 中的指数部分)。使用指数计数法的浮点数(4.1E+6)也可转换。
  • 数组 array 总是转换成字符串 "Array",因此,echo 和 print 无法显示出该数组的内容。要显示某个单元,可以用 echo $arr['foo']  这种结构。
  • 对象 object 总是被转换成字符串 "Object"
  • 资源 resource 总会被转变成 "Resource id #1" 这种结构的字符串,其中的 1 是 PHP 在运行时分配给该 resource 的唯一值。
  • NULL 总是被转变成 空字符串
  • 直接把 arrayobject 或 resource 转换成 string 不会得到除了其类型之外的任何有用信息。可以使用函数 print_r() 和 var_dump() 列出这些类型的内容。
  • 大部分的 PHP 值可以转变成 string 来永久保存,这被称作串行化,可以用函数 serialize() 来实现。如果 PHP 引擎设定支持 WDDX,PHP 值也可被串行化为格式良好的 XML 文本。
php
本作品采用《CC 协议》,转载必须注明作者和本文链接
周小帅
《L01 基础入门》
我们将带你从零开发一个项目并部署到线上,本课程教授 Web 开发中专业、实用的技能,如 Git 工作流、Laravel Mix 前端工作流等。
《G01 Go 实战入门》
从零开始带你一步步开发一个 Go 博客项目,让你在最短的时间内学会使用 Go 进行编码。项目结构很大程度上参考了 Laravel。
讨论数量: 3

补充:
单引号串变量的速度比双引号要慢

$t = microtime(true);
for($i = 0 ; $i < 100000 ; $i++) {
    $s = 'abc' . $i;
}
echo microtime(true) - $t;
echo "\n";
$t = microtime(true);
for($i = 0 ; $i < 100000 ; $i++) {
    $s = "abc{$i}";
}
echo microtime(true) - $t;

6年前 评论

@DotDotHom 运行了下,果然,还以为单引号更快呢

6年前 评论

讨论应以学习和精进为目的。请勿发布不友善或者负能量的内容,与人为善,比聪明更重要!