PHP转Go之基础数据类型对比详解

 更新时间:2023年09月17日 11:22:12   作者:全Neng攻城狮  
这篇文章主要为大家详细介绍了PHP与Go语言中基础数据类型的对比,以及使用时常见的坑,文中的示例代码讲解详细,感兴趣的小伙伴可以参考一下

本文主要讲解Go中基础数据类型,字符串、整数、浮点数、布尔这几个类型,像slice、map、struct等类型会有单独文章讲解

本文概要

  • 1、要转换思维,尽可能的不再定义弱类型,比如Go里的interface{}
  • 2、务必要注意强类型里的默认值

一、基础类型对比

我们在很多文章中都能看到类似的说明,这里copy一份,仅供参考

语言\类型booleanstringintfloatarray
PHPboolstringintfloat[1,2,3]/["a"=>1]
Goboolstringint、int8、int16、int32、int64、uint、uint8、uint16、uint32、uint64float32、float64slice/map

二、认知和使用差异点

对于强类型语言只有类型相同的值才能够比较

<?php
$a = 1;
$b = "1";
$c = true;
var_dump($a == $b);
var_dump($b == $c);
var_dump($a == $c);
// Output,当然php也支持强类型的判等比较 ===
bool(true)
bool(true)
bool(true)
package main
import "fmt"
func main() {
	a := int32(1)
	b := int64(2)
	if a == b { // 这一行直接报错,根本无法编译过去
		fmt.Println("相等")
	}
}

变量必须声明并初始化

在PHP中可以随时声明一个变量并赋予任意类型的任意值,这在Go中是行不通的,在强类型语言中,必须要提前声明变量类型,当然可以显示的声明,也可以是推导式的声明,并且Go中的所有类型都是有默认值的

package main
import "fmt"
func main() {
	var a string // 默认空字符串
	var b int // 所有int都默认0
	var c float64 // 所有float64都默认0
	d := false // 推导出d是布尔值,bool值默认false
	fmt.Println(a, b, c, d)
   // b = "1" // 这种赋值会直接报错
}
// Output, 需注意string默认值为空字符串,所以未能有效输出展示
0 0 false

protobuf中也会利用默认值的特性,不传递变量是默认值的数据,减少传输数据量

如何做类型转换

PHP中可以利用(int),(string)等方式直接完成类型强转,且不会报错,但是Go中就略显繁琐,不同的类型转到同一个类型可能使用的方法不同,比如:

package main
import (
	"fmt"
	"strconv"
)
func main() {
	a := "1"
	b := 1.0
	var c interface{}
	c = "2"
	d, _ := strconv.Atoi(a)
	f, _ := strconv.Atoi(c.(string))
	fmt.Println(int(b)) // int和float之间可以直接转换,但是要注意范围溢出的问题
	fmt.Println(d, f)   // 字符串转数字需要使用特定函数,还要注意错误
   fmt.Printf("%d %.1f", bb, b) // 其他类型转字符串,使用格式化字符串函数,最简单直观
}

Go中使用类型转换最流行的一个库就是 spf13/cast 库了,强烈建议直接引用,不要自己造轮子,需要注意的是 cast 库避免了 panic,所以在很多转换过程中,对于失败的案例,返回值就变成了变量默认值,这个需要看下自己业务场景是否正常

Unicode字符处理

在php中,Unicode字符声明时并无特殊,而仅仅是在处理时,需要使用一些列以 mb_开头的函数

<?php
$a = "我爱中国";
echo "字节长度:", strlen($a),"字符串长度:", mb_strlen($a);
// output: 字节长度:12字符串长度:4

而在Go中,Unicode对应的是一个类型 rune,而其各种操作函数跟之前没有区别 string 背后实际利用 []byte or []rune 实现,所以可以无缝互转

package main
import "fmt"
func main() {
	str := "我爱中国"
	fmt.Println("len", len(str), len([]rune(str)))
	fmt.Println(string([]rune(str)[1:])) // 如果这里不转为[]rune,则处理unicode字符时会出现乱码
}
// Output
len 12 4
爱中国

三、基础类型使用中的常见坑

1.json转换失败,引起异常

这里核心讲下类型引起的异常,其实强语言与js这种弱类型交互处理json坑真的很多

  • "1" 和 1 是完全不同的类型,golang无法解析"1"为 1, 因类型不对应,直接报错
  • {"key":null} 注意对于null,golang在解析时会解析成对应key声明的类型的默认值,而不一定是 nil
  • 不要忽略 json.Unmarshal 的报错,某个字段无法解析报错时,可能会导致结构体内都是默认值,引起异常
  • 使用 json.Unmarshal 或者 json.Marshal时,对于结构体中的小字字母开头的变量,处理时是忽略的,这个也可能会导致与预期不一致

json的处理值得写一篇单独文章来讲解,这里许个诺,稍后期待补充

2.float的精度问题

Golang中同样有浮点数精度问题的坑

package main
import (
	"fmt"
	"math/big"
)
func main() {
	f := 0.6
	ff := 0.7
	fmt.Println(f + ff)
	a, _ := new(big.Float).SetString("0.6")
	b, _ := new(big.Float).SetString("0.7")
	// 加法运算
	cccc := new(big.Float).Add(a, b)
	fmt.Println("Add:", cccc.String())
}
// Output
Add: 1.2999999999999998
Add: 1.3

可见对于高精度需求的计算时这还是有点问题的,Golang自带的math包可以有效的解决这个问题,另外推荐第三方库https://github.com/shopspring/decimal也能很好的解决这个问题,使用起来可能更方便一点~

到此这篇关于PHP转Go之基础数据类型对比详解的文章就介绍到这了,更多相关PHP转Go内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • PHP初学者最感迷茫的问题小结

    PHP初学者最感迷茫的问题小结

    列出了所有初学者最感迷茫的PHP问题,学习php的朋友可以参考下。
    2010-03-03
  • php多层数组与对象的转换实例代码

    php多层数组与对象的转换实例代码

    通过json_decode(json_encode($object)可以将对象一次性转换为数组,但是object中遇到非utf-8编码的非ascii字符则会出现问题,比如gbk的中文,何况json_encode和decode的性能也值得疑虑
    2013-08-08
  • thinkphp5.0自定义验证规则使用方法

    thinkphp5.0自定义验证规则使用方法

    本文主要讲了thinkphp5.0版本中自定义验证规则的使用方法和一些注意事项。
    2017-11-11
  • 关于在php.ini中添加extension=php_mysqli.dll指令的说明

    关于在php.ini中添加extension=php_mysqli.dll指令的说明

    关于在php.ini中添加extension=php_mysqli.dll指令的说明...
    2007-06-06
  • 比file_get_contents稳定的curl_get_contents分享

    比file_get_contents稳定的curl_get_contents分享

    相信使用过file_get_contents函数的朋友都知道,当获取的$url访问不了时,会导致页面漫长的等待,甚至还能导致PHP进程占用CPU达100%,因此这个函数就诞生了
    2012-01-01
  • Swoole 4.x服务器Server配置和函数列表

    Swoole 4.x服务器Server配置和函数列表

    Swoole是一个使用C++语言编写的基于异步事件驱动和协程的并行网络通信引擎,为PHP提供协程、高性能网络编程支持,使用同步风格实现异步程序
    本文总结了Swoole 4.x服务器预定义常量、Server配置选项、Server函数列表、Server属性列表、事件回调函数
    2024-11-11
  • PHP中非常有用却鲜有人知的函数集锦

    PHP中非常有用却鲜有人知的函数集锦

    这篇文章主要介绍了PHP中非常有用却鲜有人知的函数,结合实例形式总结分析了PHP中levenshtein、get_defined_vars、php_check_syntax、ignore_user_abort、highlight_string、highlight_file、get_browser等函数使用方法,需要的朋友可以参考下
    2019-08-08
  • 什么情况下可以不写PHP的闭合标签“?>”

    什么情况下可以不写PHP的闭合标签“?>”

    这篇文章主要介绍了什么情况下可以不写PHP的闭合标签“?>”,是进行PHP程序开发需要特别注意的地方,需要的朋友可以参考下
    2014-08-08
  • PHP 中魔术常量的实例详解

    PHP 中魔术常量的实例详解

    这篇文章主要介绍了PHP 中魔术常量的实例详解的相关资料,希望通过本文能帮助到大家,让大家理解这部分内容,需要的朋友可以参考下
    2017-10-10
  • PHP+MYSQL会员系统的开发实例教程

    PHP+MYSQL会员系统的开发实例教程

    这篇文章主要介绍了PHP+MYSQL会员系统的开发实例教程,通过一个完整的会员系统开发,进一步加深对PHP+MySQL程序设计流程的认识,需要的朋友可以参考下
    2014-08-08

最新评论