Network Security Internet Technology Development Database Servers Mobile Phone Android Software Apple Software Computer Software News IT Information

In addition to Weibo, there is also WeChat

Please pay attention

WeChat public account

Shulou

How to parse and process YAML and json format data by Ruby

2025-02-24 Update From: SLTechnology News&Howtos shulou NAV: SLTechnology News&Howtos > Development >

Share

Shulou(Shulou.com)05/31 Report--

Today, I would like to share with you how Ruby parses the relevant knowledge points of dealing with YAML and json format data, the content is detailed, and the logic is clear. I believe most people still know too much about this knowledge, so share this article for your reference. I hope you can get something after reading this article.

Ruby handles YAML

Ruby's standard library YAML is based on Psych

After require 'yaml', the to_ yaml () method is provided for most basic data types to convert objects of each data type to yaml format.

For example:

Require 'yaml'require' set'p "hello world". To _ yamlp 123.to_yamlp% w (perl shell php). To_yamlp ({one: 1, two: 2}). To_yamlp Set.new ([1m 2m 3]). To_yaml

Get:

"- hello world\ n"-123\ n "-\ n-perl\ n-shell\ n-php\ n" -\ n:one: 1\ n:two: 2\ n ""--! ruby/object:Set\ nhash:\ n 1: true\ n 2: true\ n 3: true\ n "

You can also use the YAML.dump () method to achieve the same functionality as to_yaml, which can also be written to a file.

Users = [{name: 'Bob', permissions: [' Read']}, {name: 'Alice', permissions: [' Read', 'Write']}] File.open ("/ tmp/a.yml", "w") {| f | YAML.dump (users, f)}

View the file:

-: name: Bob # = > Note that the symbols in the hash source data are preserved: permissions:-Read-: name: Alice: permissions:-Read- Write

Use YAML.load () to read data from YAML:

Require 'yaml'pp YAML.load (DATA) _ END__mysql: passwd: P@ssword1! user: root port: 3306 other1: nil other2: false other3: "" hosts:-ip: 10.10.1.1 hostname: node1-ip: 10.10.1.2 hostname: node2

Get:

{"mysql" = > {"passwd" = > "P@ssword1!", # = > Note Key is String instead of Symbol "user" = > "root", "port" = > 3306, "other1" = > "nil", "other2" = > false, "other3" = > "", "hosts" = > [{"ip" = > "10.10.1.1", "hostname" = > "node1"}, {"ip" = > "10.10.1.2", "hostname" = > "node2"]}

If you want the key of hash to be a symbol rather than a string, you can set the option symbolize_names: true:

Pp YAML.load (DATA, symbolize_names: true)

It is important to note that YAML can serialize objects, so there are several considerations:

Files involved in require are also needed during deserialization. For example, after serialization of Set types, objects cannot be restored without require 'set' during deserialization.

Some underlying objects cannot be serialized, including IO stream, Ruby code object Proc, Binding, etc.

Instead of deserializing untrusted data objects (such as data entered by the user), you can use safe_load (), which allows only the following types of data to be loaded by default:

TrueClass

FalseClass

NilClass

Numeric

String

Array

Hash

If you do want to load additional data types, you can specify the parameter permitted_classes: [] or permitted_symbols: [] in safe_load ()

Ruby processes Json data to json format string

Use JSON.generate () to convert an object or array to data in JSON format:

Require 'json'p JSON.generate "abc" p JSON.generate 123p JSON.generate truep JSON.generate nilp JSON.generate [2 name 3 junmajinlong 4] p JSON.generate ({name: "junmajinlong", age: 23}) require' set'p JSON.generate (Set.new)

Get:

"\" abc\ "" 123"true"null"[2Magne3jol 4]"{\" name\ ":\" junmajinlong\ ",\" age\ ": 23}"\ "#\"

After require 'json', many ruby types have a to_json method that can directly convert that type of data to json data:

P ({name: "junmajinlong", age: 23}). To_jsonp (Set.new ([1 Magne23: 44]). To_json

Get:

"{\" name\ ":\" junmajinlong\ ",\" age\ ": 23}"\ "#"

In addition, JSON.dump () can also convert objects to strings in JSON format, and it also supports writing to files:

Hsh = {name: "junmajinlong", age: 23} File.open ("/ tmp/a.json", "w") {| f | JSON.dump (hsh, f)} json format string is converted to Ruby object

To move from a json format string to a ruby object, there are some options that can be set, such as the * symbolize_names* option indicating whether to resolve the key in json object to a symbolic type key or, if set to false, to the key of a string.

To parse a string in json format to a Ruby data type (Hash), use JSON.parse ()

Require 'json'hsh =' {"name": "junmajinlong", "age": 23}'p JSON.parse (hsh) p JSON.parse (hsh, symbolize_names: true)

Note that the above json string must be reasonable json data, such as key must be enclosed in double quotes instead of single quotation marks, strings must be enclosed in double quotes, and so on. For example, "{'name':' junmajinlong', 'age': 23}" is not a reasonable json string.

To read json data from a json file and convert it to Ruby data, use load ():

Data = File.open ("/ tmp/a.json") do | f | JSON.load (f) endpp data#= > {"name" = > "junmajinlong", "age" = > 23} how to convert custom objects

The data types supported by json are:

String

Numerical value

Object

Array

Boolean

Null

When converting data from a language to Json data, if the data type is also supported by JSON, it can be converted directly, but if it contains a type that JSON does not support, it may report an error or be saved as an object string, depending on the corresponding implementation.

You can define an as_json instance method in the object to determine how the object is converted to a json string, and then define the class method from_json () to determine how to recover from the json string to an object.

For example,

Require 'json'require' date'class Person attr_accessor: name,: birthday def initialize name, birthday @ name = name @ birthday = DateTime.parse (birthday) endendFile.open ("/ tmp/p.json", "w") do | f | JSON.dump (Person.new ("junmajinlong", "1999-10-11"), f) end

View saved json data:

$cat / tmp/p.json "#"

Define as_json and frmo_json:

Require 'json'require' date'class Person attr_accessor: name,: birthday def initialize name, birthday @ name = name @ birthday = DateTime.parse (birthday) end def as_json {name: @ name, birthday: @ birthday.strftime ("% F")} end def self.from_json json data = JSON.parse (json) new (data ["name"], data ["birthday"]) endend

To serialize and deserialize the object later, you can:

Data = Person.new ("junmajinlong", "1999-10-11"). As_jsonp datap1=Person.from_json (JSON.dump data) p p1.birthday

If you are reading and writing json files, you can:

Person1 = Person.new ("junmajinlong", "1999-10-11") File.open ("/ tmp/p.json", "w") do | f | JSON.dump (person1.as_json, f) endp1 = File.open ("/ tmp/p.json") do | f | Person.from_json (f.read) # Person.from_json (JSON.load (f). To_json) endp p1 performance Test of several JSON parsing tools

The performance of json standard library, oj and fast_josnparser parsing json is tested. The test items include:

Load and parse json strings into ruby objects from a file

Parsing a json string into a ruby object from a memory json string

Parsing with symbolize_keys/symbolize_names conversion

Json standard library and oj dump ruby objects to json strings

Json standard library and oj save ruby object dump to json string to a file

Note:

Fast_jsonparser has no dump function, only the function of parsing json strings

When oj converts an object to an json string, it may lose the precision of data, such as the precision of floating-point numbers.

The number of json strings tested is about 50m.

Two versions of ruby 2.7.1 and ruby 3.0.1 are tested. The version information of the gem package is as follows:

Fast_jsonparser 0.5.0 json (default: 2.5.1) oj (3.11.7)

Test the code:

The require 'benchmark'require' json'require 'oj'require' fast_jsonparser'# warmjson_file='test' # file size is approximately 50Mstr = File.read (json_file) # JSONputs "load file" .center (80 '-') Benchmark.bm (30) do | x | x.report ("JSON.load:") {File.open (json_file) {| f | JSON.load (f)}} x.report ("Oj.load_file:") {Oj.load_file (json_file)} x.report ("FastJsonparser.load:") {FastJsonparser.load (json_file)} endputsputs "load file with symbolize_keys" .center (80 '-') Benchmark.bm (30) do | x | x.report ("JSON.load:") {File.open (json_file) {| f | JSON.load (f, nil, symbolize_names: true, create_additions: false)} x.report ("Oj.load_file:") {Oj.load_file (json_file, symbol_keys: true)} x.report ("FastJsonparser.load:") {FastJsonparser.load (json_file) Symbolize_keys: true)} endputsputs "parse str" .center (80,'-') Benchmark.bm (30) do | x | x.report ("JSON.parse:") {JSON.parse (str)} x.report ("Oj.load:") {Oj.load (str)} x.report ("FastJsonparser.parse:") {FastJsonparser.parse (str)} endputsputs "parse str with symbolize_keys" .center (80) '-') Benchmark.bm (30) do | x | x.report ("JSON.parse:") {JSON.parse (str, symbolize_names: true)} x.report ("Oj.load:") {Oj.load (str, symbol_keys: true)} x.report ("FastJsonparser.parse:") {FastJsonparser.parse (str, symbolize_keys: true)} endobj = JSON.parse (str, symbolize_names: true) puts puts "dump JSON to str" .center (80 '-') Benchmark.bm (30) do | x | x.report ("JSON.dump:") {JSON.dump (obj)} x.report ("Oj.dump:") {Oj.dump (obj)} endputs puts "dump JSON to file" .center (80,'-') Benchmark.bm (30) do | x | x.report ("JSON.dump:") {File.open ('0roomjson dumpies,' w') {| f | JSON.dump (obj) F)}} x.report ("Oj.to_file:") {Oj.to_file ('0roomojacked dumpies, obj)} end

Test results:

In Ruby 2.7.1:

-- load file-- user system total realJSON.load: 1.591831. 058021 1.649852 (1.738119) Oj.load_file: 1.350385 0.057684 1.408069 (2.434268)

Welcome to subscribe "Shulou Technology Information " to get latest news, interesting things and hot topics in the IT industry, and controls the hottest and latest Internet news, technology news and IT industry trends.

Views: 0

*The comments in the above article only represent the author's personal views and do not represent the views and positions of this website. If you have more insights, please feel free to contribute and share.

Share To

Development

Wechat

© 2024 shulou.com SLNews company. All rights reserved.

12
Report