begin
#some routine
rescue
retry
#on third retry, output "no dice!"
end
Je veux faire en sorte que sur le "troisième" réessayer, imprimer un message.ruby: comment savoir si le script est en 3ème tentative?
begin
#some routine
rescue
retry
#on third retry, output "no dice!"
end
Je veux faire en sorte que sur le "troisième" réessayer, imprimer un message.ruby: comment savoir si le script est en 3ème tentative?
Peut-être pas la meilleure solution, mais un moyen simple est simplement de faire une variable tries
.
tries = 0
begin
# some routine
rescue
tries += 1
retry if tries <= 3
puts "no dice!"
end
loop do |i|
begin
do_stuff
break
rescue
raise if i == 2
end
end
ou
k = 0
begin
do_stuff
rescue
k += 1
k < 3 ? retry : raise
end
Le meilleur des premières réponses ... – DigitalRoss
J'aime la première de ces alternatives parce qu'il est facile à retenir et à lire. Mais cela ne soulève pas l'erreur lors du dernier essai! – Peder
C'est vrai, le premier n'est pas adapté à la plupart des codes réseau, mais il peut être utilisé lorsqu'aucune exception ne devrait être soulevée. – glebm
class Integer
def times_try
n = self
begin
n -= 1
yield
rescue
raise if n < 0
retry
end
end
end
begin
3.times_try do
#some routine
end
rescue
puts 'no dice!'
end
Le joyau attempt est conçu pour cela, et offre la possibilité d'attendre entre les tentatives. Je ne l'ai pas utilisé moi-même, mais cela semble être une bonne idée.
Sinon, c'est le genre de choses que les blocs excelle, comme d'autres personnes l'ont démontré.
begin
#your code
rescue
retry if (_r = (_r || 0) + 1) and _r < 4 # Needs parenthesis for the assignment
raise
end
Il existe une autre gemme nommée retry-this qui aide avec une telle chose.
ruby-1.9.2-p0 > require 'retry-this'
ruby-1.9.2-p0 > RetryThis.retry_this(:times => 3) do |attempt|
ruby-1.9.2-p0 > if attempt == 3
ruby-1.9.2-p0 ?> puts "no dice!"
ruby-1.9.2-p0 ?> else
ruby-1.9.2-p0 > puts "trying something..."
ruby-1.9.2-p0 ?> raise 'an error happens' # faking a consistent error
ruby-1.9.2-p0 ?> end
ruby-1.9.2-p0 ?> end
trying something...
trying something...
no dice!
=> nil
La bonne chose au sujet d'un petit bijou par opposition à begin..rescue..retry première est que nous pouvons éviter une boucle infinie ou l'introduction d'une variable juste à cet effet.
def method(params={})
tries ||= 3
# code to execute
rescue Exception => e
retry unless (tries -= 1).zero?
puts "no dice!"
end
Proc.class_eval do
def rescue number_of_attempts=0
@n = number_of_attempts
begin
self.call
rescue => message
yield message, @n if block_given?
@n -= 1
retry if @n > 0
end
end
end
Et vous pouvez l'utiliser comme:
-> { raise 'hi' }.rescue(3)
-> { raise 'hi' }.rescue(3) { |m, n| puts "message: #{m},
number of attempts left: #{n}" }
lieu de nouvelle tentative, mettre la chose dans une boucle de 3 x? –
vous voulez réessayer dans une boucle trois fois? – puqt