Problems with the study of Ruby, the task to read from the csv file of the date (dd.mm.yyy), and after, output the dates (all dates of the 21st century) that come before and, separately, which come after the entered date. So far, I was able to implement only the reading (and that is crooked in my opinion) and output. Stuck on trying to sort them. (In the 3 dates file 05/12/2021 1/21/2016 12/23/2019) file http://rghost.ru/88rySyvnc

require 'CSV' require 'date' require 'twitter_cldr' class Date sort_date = gets sort_date1 = sort_date.split('<br>').map(&:strip).map { |d| DateTime.parse(d) } file = File.new("date.csv") file.each do |line| line.split('.').last.to_i date = line.split('<br>').map(&:strip).map { |d| DateTime.parse(d) } date1 = date puts "#{date1}" end end 
  • class Date <- uh, why? - D-side
  • Bring the CSV file itself, by the way. It will be much easier to explain the essence of errors, seeing the source data and knowing the result. - D-side
  • Class just created. In principle, it is possible without it - user206618
  • already corrected. two end just did not copy))) - user206618
  • @ user206618 You actually have the file.each do | line | not closed Class you do not have to? - cheops

3 answers 3

A single-column CSV can be processed by counting the value of the entire line , so if you have such a file:

 12.05.2021 21.01.2016 23.12.2019 

Can:

 sorted_dates = File.readlines('dates.csv') # Получили массив строк из файла .map { |x| Date.parse(x) } # Преобразовали каждую строку в дату .sort # ... .map { |d| d.strftime('%d.%m.%Y') } # Обратно в строки с форматом 

Since you want to do some manipulations with dates, you will want to postpone the last .map until you want to make a result. Dates have a great comparison operator and lots of other useful methods.

An array can be filtered / flipped / transformed with the whole Enumerable arsenal .

    1. No need to define a Date class. This class is in the standard library. If you need a class for the implementation of the main logic (this is a normal approach), then you should call it differently and more semantically.
    2. You do not need to declare a class just to perform some kind of algorithm in the body.
    3. The standard library has a class for working with CSV . If the task requires working with a file as with CSV, it makes sense to use it.
    4. If I understand correctly, you do not need to sort the dates.

    Here is an example class

    Using:

     parser = CsvDateParser.new("/path/to/file/date.csv") p 'greater' parser .greater_than(Date.parse("2017-01-01")) .each { |element| puts element } 

    Will display

    "greater"

    2021-05-12

    2019-12-23

     p "less" parser .less_than(Date.parse("2017-01-01")) .each { |element| puts element } 

    Will display

    "less"

    2016-01-21

     p "all" parser .all .each { |element| puts element } 

    =>

    "all"

    2021-05-12

    2016-01-21

    2019-12-23

      You can sort the dates in the format given by you (DD.MM.YYYY) as follows

       require 'CSV' date = '21.01.2016' day, month, year = date.split '.' dates = CSV.read('date.csv').collect{|x| x[0]}.sort do |x, y| xday, xmonth, xyear = x.split '.' yday, ymonth, yyear = y.split '.' "#{yyear}.#{ymonth}.#{yday}" <=> "#{xyear}.#{xmonth}.#{xday}" end.reject do |date| xday, xmonth, xyear = date.split '.' "#{year}.#{month}.#{day}" < "#{xyear}.#{xmonth}.#{xday}" end p dates 
      • Does not sort the same? - user206618
      • @ user206618, do you have such a result? ["05/12/2021", "12/23/2019", "01/21/2016"], if you need to sort the reverse order, swap the lines in the <=> operator. Sorting is by year, then by month, then by day. - cheops pm
      • oops. Yes. did not notice that sorts, but not in that order))) - user206618
      • Corrected the answer. - cheops
      • and how can you make a comparison with the entered? - user206618