2008-09-10 45 views
17

我有一些Ruby代碼這需要在格式的命令行日期:的最佳方式

-d 20080101,20080201..20080229,20080301

哪意味着我想運行20080201和20080229(含)之間的所有日期以及列表中的其他日期。

鑑於我可以得到字符串20080201..20080229什麼是最好的方式來將其轉換爲範圍的實例。目前我正在使用eval,但感覺應該有更好的方法。

@Purfideas我是尋找一個更通用的答案,將任何類型的int ..int字符串轉換爲我猜的範圍。

回答

14

但後來就去做

ends = '20080201..20080229'.split('..').map{|d| Integer(d)} 
ends[0]..ends[1] 

反正我是不推薦的eval,出於安全原因

+0

什麼是涉及使用eval安全原因? – 2008-09-10 08:23:42

+1

cmd行輸入是「用戶輸入」,所以你可以這樣總是得到可信任的人執行嗎?這是最初的SQL注入...在安全性方面問這個問題......這將是你有史以來的最高分。 :) – Purfideas 2008-09-10 17:15:18

2

假設你要的範圍內,通過幾個月等正常循環,儘量

require 'date' 

ends = '20080201..20080229'.split('..').map{|d| Date.parse(d)} 
(ends[0]..ends[1]).each do |d| 
    p d.day 
end 
7

注入無參數適用於兩個元素陣列:

rng='20080201..20080229'.split('..').inject { |s,e| s.to_i..e.to_i } 

當然,這可以由通用

class Range 
    def self.from_ary(a) 
    a.inject{|s,e| s..e } 
    end 
end 

rng = Range.from_ary('20080201..20080229'.split('..').map{|s| s.to_i}) 
rng.class # => Range 
31
Range.new(*self.split("..").map(&:to_i)) 
0

結合@Purfideas另一個答案在計算器上的某個地方回答,我解決了這個由周圍也與輸入校驗碼,所以使用的唯一的事情是一個有效的枚舉

if !value[/^[0-9]+\.\.[0-9]+$/].nil? 
    ends = value.split('..').map{|d| Integer(d)} 
    value = ends[0]..ends[1] 
end 

它基本上重寫您的字符串值爲一個枚舉值。如果您在yaml配置文件中添加可枚舉字段,這很方便。

如果您的應用程序需要它,您可以使用可選的第三個字面點來擴展正則表達式,這可以是可選的。

0

如果我們不喜歡它

v= "20140101..20150101" 
raise "Error: invalid format: #{v}" if /\d{8}\.\.\d{8}/ !~ v 
r= eval(v) 

和攻擊者繞過提高檢查(簡單地通過操縱運行時關閉異常的方式)的方式,然後我們就可以得到一個危險的eval,這將潛在地破壞宇宙。

因此減少攻擊向量的緣故,我們檢查格式,然後手工做解析,然後檢查結果

v= "20140101..20150101" 
raise "Error: invalid format: #{v}" if /\d{8}\.\.\d{8}/ !~ v 
r= Range.new(*v.split(/\.\./).map(&:to_i)) 
raise "Error: invalid range: #{v}" if r.first> r.last 
1

有這個here的瑰寶。使用正則表達式來驗證字符串(沒有SQL注入恐懼),然後評估。

0

這裏假設您希望將散列存儲爲系統常量值並將其存儲在任何模型中。散列鍵將是一個範圍值。

hash_1 = {1..5 => 'a', 6..12 => 'b', 13..67 => 'c', 68..9999999 => 'd'} 

然後創建系統常量,其值爲hash_1.to_json。 .to_json會將您的哈希對象轉換爲JSON對象。 現在裏面的代碼創建一個新的哈希hash_2,

JSON.parse(SystemConstant.get('Constant_name')).each{|key,val| temp_k=key.split('..').map{|d| Integer(d)}; hash_2[temp_k[0]..temp_k[1]] = val} 

新hash_2將所需hash_1