就冲 golang 可以生成二进制单文件这一点,部署方便,想试试
拿 beego 练个手,用了它的 httplib 模块,其中, request 后有个直接将结果转换成 json 的,原文如下:
解析为 JSON 结构, req.ToJSON(&result) 方法
返回结构直接解析为 JSON 格式,解析到 result 对象中
我!以!为!这是和 py 的 json.loads()一样,心理窃喜,接下来……
我传了个 string ,没数据,传个空接口,没数据。。。。。
看了下源码,是直接调用的 json.Unmarshal(data, v),属于 golang 自带的库,可我一搜……
竟然发现,需要提前定义 json 的结构???而且字段首字母必须大写???不然还得声明???
WTF
beego 的 request 可以返回 string ,像 py 的 requests.get(url).text ,但是我不想这样,我想 json.loads(requests.get(url).text)
我就是想获取个 json 而已,能不能不要这么折腾人?
1
Allianzcortex 2016-12-29 23:10:07 +08:00 1
Go 是静态语言,在解析 JSON 上是没有 Python 有优势的
|
2
phrack 2016-12-29 23:26:29 +08:00 via Android
难道你第一门语言是 py 不是 c ´・ᴗ・`
|
3
icedx 2016-12-29 23:33:09 +08:00 1
其实就是一个入乡随俗的道理
顺便 Python 是鸭子类型 这是没有这个特性的语言比不了的 |
4
choury 2016-12-29 23:33:15 +08:00 via Android
你是没用过 C , java 这些吧
|
5
scnace 2016-12-29 23:42:38 +08:00
试试解析到 map 里面(嘿嘿嘿
|
6
TheCure 2016-12-29 23:45:02 +08:00
simplejson
|
7
defia 2016-12-29 23:45:13 +08:00
可以 map[string]interface{}吧
|
8
gouchaoer 2016-12-29 23:45:57 +08:00 via Android
静态语言里不如 rust
|
9
nicevar 2016-12-29 23:47:27 +08:00
哈哈,如果让你用 c 来处理 json 会不会上吊了
|
10
only0jac OP |
11
Tyanboot 2016-12-29 23:59:14 +08:00 via Android
看
|
12
scnace 2016-12-30 00:02:12 +08:00 1
就是不用`struct`的形式了 而是采用`map[string]interface{}`的形式呀。然后`Unmarshal`之后 map 的 key(string)就是 json 的 key map 的 value 就是 json 的 value 惹 。 但是 我还是建议解析到 struct 的 代码可维护性会强很多(不要问我怎么知道的
|
13
Tyanboot 2016-12-30 00:03:41 +08:00 via Android 1
@Tyanboot 不好意思手抖按到回复了…
我觉得看库的实现吧 c#有个 NewtonJson 。也是需要先有个定义好的类来做载体,才能解析到定义好的类的实例上。也就是需要先声明 JSON 的字段格式。 但是 c++是有个 jsoncpp 的库,不需要定义 JSON 的格式,用起来要舒服不少。 |
14
messyidea 2016-12-30 00:08:14 +08:00 1
|
15
limhiaoing 2016-12-30 00:20:07 +08:00 via iPhone 1
json 反序列化成 struct 难道不是很方便的功能吗,而且一般不会强制要求必须定义结构体。这个能力一般都是用反射来实现的,楼上说的 C++现阶段要实现并不容易,可能至少需要静态反射标准化后才能做到。 rust 之前用过一个 json 库也有这个特性,不知道是怎么实现的。
|
16
soli 2016-12-30 00:27:15 +08:00
知足吧。
别说 JSON ,你用 C 拼个字符串试试。 |
17
eyp82 2016-12-30 00:29:46 +08:00
python 党笑而不语
|
18
reus 2016-12-30 00:32:44 +08:00 2
定义一个结构体很麻烦吗?
var data struct { // xxx } 定义变量的时候就可以定义 struct ,或者说 go 的 struct 可以是匿名的 在静态类型语言里, go 处理 json 是最方便的了,因为有 reflection 别用什么 map[string]interface{},处理嵌套的结构你就知道了 var data struct { List []struct{ Info struct { // xxx } } } 你用 map[string]interface{}试试?类型转换烦死你。 再说回来,想学 go 就直接学标准库,别像学 py 一样,上来就框架。 go 的标准库功能比 py 的强得多,根本不需要 beego 这种东西。 |
19
kkk330 2016-12-30 00:35:33 +08:00 1
- 函数签名是 json.Unmarshal(data []byte , v interface{})
- 也就是说 lz 你想简单点就直接 ```go data := []byte("{"a":"a", "b": 1}") var v interface{} json.Unmarshal(data , v) fmt.Println(v) ``` |
20
jsq2627 2016-12-30 00:35:52 +08:00 via iPhone
@Tyanboot 你说的只是 newtonjson 的一种早期强类型用法。现在是可以反序列化成 dynamic 类型,或者 jtoken 类型配合 linq 很方便。
虽然我没用过 go 但我觉得一定存在一种不需要预先定义 schema 的使用方式的。 |
21
est 2016-12-30 00:36:51 +08:00
map[interface{}]interface{} 大法好。
另外静态语言里搞一个 [1, "1", None, {1: 2, None: 0, 2: 3}] 好像是不可能实现的。。 |
24
orvice 2016-12-30 01:08:38 +08:00
首字母大写是因为不大写 json 包就获取不到成员的值了。
|
25
orvice 2016-12-30 01:13:43 +08:00
也不一定要定义结构体啦,也可以用 map[string]interface{} 但是类型转换会烦死人、。。
|
27
Reficul 2016-12-30 02:01:32 +08:00 via Android 1
等到接手一个老项目,不知道传过来的 JSON 里面元素有哪些的时候,就能感叹动态一时爽的道理了
|
28
yegle 2016-12-30 03:08:20 +08:00
@est
可以实现,就是麻烦一点。你需要用一个 struct 来 hold 所有可能的值(类似 C union ),然后自己写 marshal/unmarshal 。 |
29
vizee 2016-12-30 03:24:07 +08:00
好的, 那就不用
|
30
ericls 2016-12-30 03:46:25 +08:00 via iPhone
我喜欢了很多的语言 是不是不够上道
|
31
keysona 2016-12-30 04:12:24 +08:00
更有有点吧。
看你是要性能还是轻松了。 大部分情况下我会选择轻松。 |
32
huodon 2016-12-30 06:19:30 +08:00 via Android 1
底子太差。。。
|
34
jingniao 2016-12-30 07:41:03 +08:00 via Android
静态偏底层的处理,意味着 python 隐藏的的一些细节, go 中你得自己来处理。
昨天学习 go ,重写一个 python 模块,代码量至少两倍。 |
35
assassinpig 2016-12-30 07:56:51 +08:00 via Android
Go 不适合 LZ
|
36
MushishiXian 2016-12-30 08:09:30 +08:00
.....这有啥好吐槽的,你怎么不说性能
|
37
only0jac OP @messyidea 感谢,这篇很详细,回去仔细看看
@limhiaoing 方便吗,如果返回的 json 有 100 个字段,难道我 struct 里也需要跟着定义 100 个吗(假设这 100 个字段都有用) |
38
only0jac OP |
39
jeffersonpig 2016-12-30 08:43:42 +08:00
最不能忍的是 go 强制{}的对齐方式, WTF
|
40
limhiaoing 2016-12-30 08:45:34 +08:00 via iPhone
@only0jac
你非要着眼于不方便的地方不用就是了! |
43
kingddc314 2016-12-30 09:08:51 +08:00 via Android
静态语言就这样,要习惯,至少 Go 还有反射。当初 C/C++拼装解析 JSON 那才是一个痛苦,只是后来的 C++11 特性才好一丁点
|
44
ry_wang 2016-12-30 09:21:06 +08:00 1
不想定义结构体还想用着简单, https://github.com/tidwall/gjson 啊。
|
45
Immortal 2016-12-30 09:26:50 +08:00
静态语言都这样,不知道吐槽点在哪里. 既然选择了静态语言 势必要牺牲一些便携性 多写两行代码 空间换时间
而且看标题我以为是来夸 go 的... |
46
pubby 2016-12-30 09:41:53 +08:00 via Android
我猜应该有工具能输入复杂样本自动生成结构定义的
有些比较麻烦的地方是 type JobTime time.Time 必须自己实现一遍 Marshal/Unmarshal |
47
Citrus 2016-12-30 09:48:25 +08:00
前几楼不要乱黑啊,虽然个人不喜欢 Java ,但是 Java 反序列化 Json 还真不需要定义啊,而且有很多方法。
1. 直接反序列化成 Map<String, String> ,最粗暴,但是对某些 Json 结构支持不好 2. 直接反序列化成 JSONObject ,完美方案 |
50
kkk330 2016-12-30 10:08:01 +08:00 1
|
51
mengzhuo 2016-12-30 10:17:08 +08:00
首先,静态语言就是这样的……
100 项可以用 go generate 自动生成,首字母大写可以用 type A struct { ST `json:"st"` } |
52
likexian 2016-12-30 10:20:59 +08:00 1
|
53
mengzhuo 2016-12-30 10:25:12 +08:00 1
而且不一定要定义完 result ,你需要什么数据,就定义什么好了
比如 { "A": 1, "B": 2, "C": "OK", } 你的处理函数只需要里面的 C 的话, type Result struct { C string json.RawMessage } 具体请看官方标准库, https://golang.org/pkg/encoding/json/#example_RawMessage |
55
sampeng 2016-12-30 10:37:36 +08:00
我觉得这是是语言的哲学决定的。
golang 的开发者觉得,开发语言不能有歧义,如果是不需要定义结构体。真的,在项目里面看到各种 json 对象乱飞,都不知道哪来得时候就很痛苦。 定义结构体最大的好处是语言自文档化,光看代码就能了解整个逻辑。现在特别反感在代码里绕圈子的。简直是折磨 想想 golang 连方法重载这种特性都没有就能理解了。。 |
56
tairan2006 2016-12-30 10:37:59 +08:00 via Android
楼主你没写过静态语言么… 实际上可以用匿名 struct 的,不一定要预定义
|
57
dreamtrail 2016-12-30 11:02:25 +08:00 1
其实静态语言也没那么可怕,你只要写一次,以后直接复制代码修改一下就行了,虽然还是比不上脚本但也不是想象的那么麻烦。
|
58
gamexg 2016-12-30 11:56:40 +08:00 2
python 转 go
go 的 json 也是可以不先定义结构,但是每次使用时的检查和转换烦死人,静态类型语言都有这个问题。 不过现在觉得这是一个好的特征,只用定义好结构,然后 json 解析到结构一次就能够确定 json 符合预期,之后就不用每个字段都检查一次了。 另外搜索 generate go struct from json ,直接有在线网站提供根据 json 自动生成 go 结构,直接用即可。 python 时就已经是动态一时爽,重构火葬场了。 每次接口修改字段都需要检查很多地方,悲剧的是 ide 搜索不是找到不相关的就是漏下一些。 静态语言 ide 可以轻松找出来哪些地方引用了接口的结构。 只要确定结构定义处改了,即使有忘了的地方编译时自动报错。 |
59
magicdawn 2016-12-30 12:00:59 +08:00
C# 都有 dynamic
|
62
ispinfx 2016-12-30 12:07:48 +08:00 via iPhone
人生苦短 我用 Python
|
63
moliliang 2016-12-30 12:10:26 +08:00
golang 大法好,无需 bb ,,,哈哈哈
|
64
boneyao 2016-12-30 12:26:47 +08:00
定义一个结构体很麻烦吗?
定义一个不麻烦,但是定义 100 个的时候感觉快崩溃了。 |
65
lijiac 2016-12-30 12:28:14 +08:00
乍看标题以为楼主要黑我 python ,正准备撸起袖子大干一场,结果...
|
66
zhiyong 2016-12-30 12:54:45 +08:00 1
看看 github.com/tidwall/gjson 这个库,或许能帮到你!
|
67
shyling 2016-12-30 12:55:34 +08:00
我知道楼主喜欢那种 JsonObject.getXX("name").getYY("name")那种 0v0
|
68
rrfeng 2016-12-30 12:57:37 +08:00
有这样的 json 库。
但是怎么说呢…… |
69
coldwinds 2016-12-30 13:30:28 +08:00 via Android
入乡随俗
|
70
levn 2016-12-30 13:36:42 +08:00
先在静态语言里实现一个动态语言……然后……
|
71
fcfangcc 2016-12-30 13:45:12 +08:00 1
json.loads(requests.get(url).text) 可以 requests.get(url).json()
|
72
woniuge 2016-12-30 13:48:05 +08:00 2
|
73
Immortal 2016-12-30 13:56:34 +08:00 1
再说一句
不需要定义结构体的用法 map[string]interface{} 还有 golang 的常用 json 库 上面说的 gjosn 还有一个 simplejson 前者性能更高一些 能直接 get json 里的字段 |
74
fuyufjh 2016-12-30 14:04:57 +08:00 2
如果结构已知, dict 毕竟要查找,效率和 struct 不能比的。作为一门可以编译到二进制的强类型语言,当然是 struct
如果结构不定,就要传 map[string]interface{}进去 不带你这样不会用就黑的。。 |
75
9 2016-12-30 14:13:39 +08:00
@only0jac lz 可以看看跟你类似的吐槽 https://www.v2ex.com/t/98585
|
76
taowen 2016-12-30 15:43:33 +08:00
可以看一下我写的 jsoniter http://jsoniter.com/java-features.html 解析各种 json 应该要方便很多了
这个是 java 版本的文档, golang 版本的稍后更新 |
77
gouchaoer 2016-12-30 16:57:51 +08:00 via Android
易语言可以生成二进制呢
|
78
qwer1234asdf 2016-12-30 17:00:33 +08:00
最蛋疼的是改数据结构, struct 越改越乱。。。
|
79
only0jac OP |
80
a7a2 2016-12-30 17:34:52 +08:00
写吧 多写点 以后就可以复制粘贴了 那些什么编程语言都用过的人 都是复制粘贴的
程序员不可能同时专注几种语言的 写 java 三年 然后 python 三年 然后 go 三年 这个时候忘掉了 Java 的了。。。 |
81
incompatible 2016-12-30 17:38:13 +08:00 via iPhone
@est 搞出「 [1, "1", None, {1: 2, None: 0, 2: 3}] 」这种非标 json 的必要性是?
|
82
billlee 2016-12-30 20:51:50 +08:00
只是不同的设计模式而已,就像 Java 的 org.json 与 Jackson 的区别。
|
83
est 2016-12-30 21:47:02 +08:00
|
84
pathbox 2016-12-31 11:39:09 +08:00
静态语言和动态语言的区别。你静态语言不过关啊 lz
|
85
mengskysama 2017-01-01 01:57:46 +08:00
用 go 写 api 真心累,特别是操作大量 json 的时候不如 node 和 py 灵活。用了十来个框架下来最喜欢的是 koa ,性能开发效率兼备,至于部署的话...都不是个问题。
|
86
only0jac OP @mengskysama go 部署简单啊,最后只有一个二进制文件, py 部署还得装环境,装虚拟空间, node 没用过,不知道怎么部署
|
87
reyoung1110 2017-01-01 20:49:21 +08:00
|
88
freestyle 2017-02-12 17:24:36 +08:00
确实,Python 解析 json 比 GO 方便多了
golang 得定义好结构体, 否则用 map[string]interface{} 的话要用的时候每一层都得类型转换.不过 JSON 格式本来就比较灵活,嵌套的话要写一大把结构体-_- response.Result.(map[string]interface{})["files"].([]interface{})[0].(map[string]interface{})["path"].(string) 另外大写是 go 的机制,大写的才能访问到, 可以用结构体注解表示序列化后的小写 key type Aria2JsonRPCReq struct { Method string `json:"method"` Jsonrpc string `json:"jsonrpc"` Id string `json:"id"` Params []interface{} `json:"params"` } |