Extracing words from a string? - ruby

I have a string "---\n- bb\n- j2me\n". I want to extract the words and save it into an array. Like ['bb','j2me']. I tried the below but its not working.
"---\n- bb\n- j2me\n".split("\n")
If you have any idea please share.

That looks like YAML:
puts "---\n- bb\n- j2me\n"
# ---
# - bb
# - j2me
You can parse it with:
require 'yaml'
YAML.load("---\n- bb\n- j2me\n")
#=> ["bb", "j2me"]

Related

ruby yaml don't remove header %YAML 1.1

I have a array in ruby named array, I aded value into yaml file, but after in file.yml, it remove me %YAML 1.1, so I won't
yaml_string = File.read "file.yaml"
data = YAML.load yaml_string
array.each do |value|
data["title"] <<"- "+value+"\n"
end
output = YAML.dump data
File.write("file.yaml", output)
before execution, the header is present, but after execution it remove it (%YAML 1.1) and all lines comment with #, so I won't
I think something like this is what you're trying to do.
I'm assuming your yaml array of titles matches your array object.
Otherwise you could just use something like Enum#with_index if you just want to map the number of the yaml array to the text.
require 'psych'
filename = "sample_yaml.yml"
array = [0, 1, 2, 3]
if File.exists?(filename)
puts "File exists. :) Parsing the yaml file."
yaml = Psych.load_file(filename)
array.each do |value|
yaml[value]["title"] << " - #{value}" # find the title that matches the index number of array
end
else
raise ArgumentError, "bad file name"
end
puts "Outputting to reformatted yaml file"
File.open("reformatted_file.yaml", 'wb') {|f| f.write "%YAML 1.1\n" + Psych.dump(yaml)}
assuming yaml file like such
---
- title: zero
- title: one
- title: two
- title: three
Outputs
---
- title: zero - 0
- title: one - 1
- title: two - 2
- title: three - 3

Apply .capitalize on an Cyrillic array in ruby

I want to capitalise the string elements in the array with ruby
This is my code:
headermonths = ["января","февраля","марта","апреля","мая","июня","июля","августа","октября","ноября","декабря"]
headermonths.each {|month| month.capitalize!}
puts headermonths
I get the following output:
января
февраля
марта
апреля
мая
июня
июля
августа
октября
ноября
декабря
if print the array with:
print headermonths
I get the following
["\u044F\u043D\u0432\u0430\u0440\u044F", "\u0444\u0435\u0432\u0440\u0430\u043B\u044F", "\u043C\u0430\u0440\u0442\u0430", "\u0430\u043F\u0440\u0435\u043B\u044F", "\u043C\u0430\u044F", "\u0438\u044E\u043D\u044F", "\u0438\u044E\u043B\u044F", "\u0430\u0432\u0433\u0443\u0441\u0442\u0430", "\u043E\u043A\u0442\u044F\u0431\u0440\u044F", "\u043D\u043E\u044F\u0431\u0440\u044F", "\u0434\u0435\u043A\u0430\u0431\u0440\u044F"]
But I would like to have an output like:
Января
Февраля
Марта
Апреля
Мая
Июня
Июля
Августа
Октября
Ноября
Декабря
How does I achieve this with a ruby method?
You can use the unicode gem
require 'unicode'
headermonths = ["января","февраля","марта","апреля","мая","июня","июля","августа","октября","ноября","декабря"]
headermonths.map! {|month| Unicode::capitalize month }
puts headermonths
# >> ["Января", "Февраля", "Марта", "Апреля", "Мая", "Июня", "Июля", "Августа", "Октября", "Ноября", "Декабря"]
Stand-alone solution :
# From : https://en.wikipedia.org/wiki/Cyrillic_alphabets :
upcase = "АБВГДЕЖЗИЙКЛМНОПРСТУФХЦЧШЩЬЮЯ"
downcase = "абвгдежзийклмнопрстуфхцчшщьюя"
headermonths = ["января","февраля","марта","апреля","мая","июня","июля","августа","октября","ноября","декабря"]
headermonths.each{|word| word[0] = word[0].tr(downcase,upcase)}
# => ["Января", "Февраля", "Марта", "Апреля", "Мая", "Июня", "Июля", "Августа", "Октября", "Ноября", "Декабря"]
If you want to use it with words in latin and cyrillic alphabets :
headermonths.each{|word| word[0] = word[0].tr(downcase,upcase).upcase }
With ActiveSupport
You can use ActiveSupport::Multibyte :
require 'active_support/core_ext/string/multibyte'
"января".mb_chars.capitalize.to_s #=> "Января"
So your script becomes :
require 'active_support/core_ext/string/multibyte'
headermonths = ["января","февраля","марта","апреля","мая","июня","июля","августа","октября","ноября","декабря"]
headermonths.map!{|word| word.mb_chars.capitalize.to_s}
#=> ["Января", "Февраля", "Марта", "Апреля", "Мая", "Июня", "Июля", "Августа", "Октября", "Ноября", "Декабря"]
Ruby 2.4
The code in your question would work just as expected with Ruby 2.4.
See "Case sensitivity for unicode characters" here.
The example below is a robust capitalize version, that works in any ruby starting with 1.9 but for cyrillic only due to -32 hardcoded.
NB: thanks and credits go to #Stefan and #EricDuminil, who lead me to the right direction
headermonths = %w|января февраля марта апреля мая июня
июля августа октября ноября декабря|
puts (headermonths.each do |s|
s[0] = (s[0].ord - 32).chr(Encoding::UTF_8)
end.inspect)
#⇒ ["Января", "Февраля", "Марта", "Апреля", "Мая", "Июня",
# "Июля", "Августа", "Октября", "Ноября", "Декабря"]

Can I manipulate yaml files and write them out again

I have a map of values, the key is a filename and the value is an array strings.
I have the corresponding files
how would I load the file and create a fixed yaml value which contains the value of the array whether or not the value already exists
e.g.
YAML (file.yaml)
trg::azimuth:
-extra
-intra
-lateral
or
trg::azimuth:
[extra,intra,lateral]
from
RUBY
{"file.yaml" => ["extra","intra","lateral"]}
The YAML documentation doesn't cover its methods very well, but does say
The underlying implementation is the libyaml wrapper Psych.
The Psych documentation, which underlies YAML, covers reading, parsing, and emitting YAML.
Here's the basic process:
require 'yaml'
foo = {"file.yaml" => ["extra","intra","lateral"]}
bar = foo.to_yaml
# => "---\nfile.yaml:\n- extra\n- intra\n- lateral\n"
And here's what the generated, serialized bar variable looks like if written:
puts bar
# >> ---
# >> file.yaml:
# >> - extra
# >> - intra
# >> - lateral
That's the format a YAML parser needs:
baz = YAML.load(bar)
baz
# => {"file.yaml"=>["extra", "intra", "lateral"]}
At this point the hash has gone round-trip, from a Ruby hash, to a YAML-serialized string, back to a Ruby hash.
Writing YAML to a file is easy using Ruby's File.write method:
File.write(foo.keys.first, foo.values.first.to_yaml)
or
foo.each do |k, v|
File.write(k, v.to_yaml)
end
Which results in a file named "file.yaml", which contains:
---
- extra
- intra
- lateral
To read and parse a file, use YAML's load_file method.
foo = YAML.load_file('file.yaml')
# => ["extra", "intra", "lateral"]
"How do I parse a YAML file?" might be of use, as well as the other "Related" links on the right side of this page.

Use file's contents in Ruby

My "information" file includes following hash.
student_balances = {"Jane Doe"=>1000, "Jim Doe"=>6200, "John Newman"=>73282, "Leonard Smith"=>3992, "Loe Newton"=>5643, "Eric"=>34234}
I want to import this "information" file into my main program and use its contents right away.
file_location = "Ruby/account.rb"
f = File.open(file_location, "r+")
student_balances.each do |key, value|
puts "#{key} : #{value}"
end
I can't figure out how.
I would suggest to store the data in another format like YAML. It is more readable and easier to write:
# in balances.yml
"Jane Doe": 1000
"Jim Doe": 6200
"John Newman": 73282
"Leonard Smith": 3992
"Loe Newton": 5643
"Eric": 34234
Read the file with:
require 'yaml'
balances = YAML.load_file('balances.yml')
When the input files contains the following string and you will like
to import the string in a ruby variable you first have to evaluate the
string. Then you can use the variables as an array
student_balances = nil
DATA.readline.each do | line |
eval line
puts student_balances
end
__END__
student_balances = {"Jane Doe"=>1000, "Jim Doe"=>6200, "John Newman"=>73282, "Leonard Smith"=>3992, "Loe Newton"=>5643, "Eric"=>34234}

Can't correctly use external text file the way I used a literal list

I move a comparison of a list of words to a text file which I now try to bring in using IO.gets on each line. This has completely altered my results.
Basically I'm using a Trie to figure out if a prefix is inside a word - now my output is only showing the prefixes which means none of them are "matching" correctly and defaulting to returning all of the prefixes.
Is this an encoding issue or what's going on?
Here's the specific code I'm speaking of - so as opposed to:
sources = ['Bash', 'cplusplus', 'java', 'javascript', 'php', 'python', 'ruby']
prefixes = ['ab', 'ba', 'bu', 'Jav', 'ph', 'ru', 'ze']
I do this now:
def fileList(dir, array)
file = File.new(dir, "r")
while (line = file.gets)
array << line
end
end
sources = Array.new
prefixes = Array.new
fileList("../lists/sources.list", sources)
fileList("../lists/prefixes.list", prefixes)
With each element having its own line in the text file
https://github.com/jphenow/merge_prefix/tree/master/ruby
Thanks a ton for any help!
It's not real clear what you are trying to accomplish, but here's how to read the lines of files and append them to an array, which is a common-enough task:
The source files look like:
sources.list:
Bash
cplusplus
java
javascript
php
python
ruby
and
prefixes.list:
ab
ba
bu
Jav
ph
ru
ze
The code looks like:
require 'pp'
def fileList(dir, array)
array += File.readlines(dir).map(&:chomp)
end
sources = Array.new
prefixes = Array.new
pp fileList("sources.list", sources)
pp fileList("prefixes.list", prefixes)
=> ["Bash", "cplusplus", "java", "javascript", "php", "python", "ruby"]
=> ["ab", "ba", "bu", "Jav", "ph", "ru", "ze"]
Try this:
def file_list(dir, array)
Dir.chdir dir
Dir.glob("*").each{|file| array << file}
end
It's unusual for a method to change a variable's value but it will happen because of a quirk of array#<<. It's more common for the method to return the value:
def file_list(dir, array)
Dir.chdir dir
array + Dir.glob("*")
end
sources = fileList("./somedir", sources)

Resources