J'ai une valeur qui sera l'une des quatre choses suivantes: boolean true, boolean false, la chaîne "true" ou la chaîne "false". Je veux convertir la chaîne en booléen s'il s'agit d'une chaîne, sinon laissez-la inchangée. En d'autres termes:
"vrai" devrait devenir vrai
"false" devrait devenir faux
vrai devrait rester vrai
false doit rester faux
true
oufalse
ou est - il suffisant si le résultat est truthy ou Falsey? Si ce dernier, alorsfalse
est déjà faux, et les deuxtrue
et'true'
sont véridiques, donc la seule valeur pour laquelle le résultat n'est pas déjà correct est'false'
:if input == 'false' then true else input end
devrait le faire.!!(if input == 'false' then true else input end)
. Le second!
convertit la valeur de retour en un booléen qui est l'opposé de ce que vous voulez; le premier!
fait alors la correction. Ce "truc" existe depuis longtemps. Tout le monde ne l'aime pas.Réponses:
la source
obj.to_s.downcase == 'true'
downcase!
et vous allouerez 1 objet de moins.downcase
dupliquera la chaîne existante. Lorsque Frozen String Literals devient une option par défaut de Ruby, cela importera moins.Si vous utilisez Rails 5, vous pouvez faire
ActiveModel::Type::Boolean.new.cast(value)
.Dans Rails 4.2, utilisez
ActiveRecord::Type::Boolean.new.type_cast_from_user(value)
.Le comportement est légèrement différent, comme dans Rails 4.2, la vraie valeur et les fausses valeurs sont vérifiées. Dans Rails 5, seules les fausses valeurs sont vérifiées - à moins que les valeurs ne soient nulles ou correspondent à une valeur fausse, on suppose que c'est vrai. Les fausses valeurs sont les mêmes dans les deux versions:
FALSE_VALUES = [false, 0, "0", "f", "F", "false", "FALSE", "off", "OFF"]
Rails 5 Source: https://github.com/rails/rails/blob/5-1-stable/activemodel/lib/active_model/type/boolean.rb
la source
FALSE_VALUES
dans Rails comprenne également "non".ActiveRecord::Type::Boolean::FALSE_VALUES << "no"
à un initialiseur.ActiveModel::Type::Boolean.new.cast(value)
est sensible à la casse ... donc 'False' sera évalué à vrai comme n'importe quelle autre chaîne sauf 'false'. les chaînes vides sont''
par défaut nulles et non fausses. ^^ informations précieuses fournies ici par @thomasfedb sur la personnalisation de l'initialiseurActiveModel::Type::Boolean.new.cast(nil)
retourne égalementnil
.ActiveRecord::Type::Boolean::FALSE_VALUES
est gelée.J'ai fréquemment utilisé ce modèle pour étendre le comportement de base de Ruby afin de faciliter la conversion de types de données arbitraires en valeurs booléennes, ce qui facilite grandement la gestion des différents paramètres d'URL, etc.
Alors disons que vous avez un paramètre
foo
qui peut être:Au lieu d'utiliser un tas de conditions, vous pouvez simplement appeler
foo.to_boolean
et il fera le reste de la magie pour vous.Dans Rails, j'ajoute ceci à un initialiseur nommé
core_ext.rb
dans presque tous mes projets car ce modèle est si courant.la source
"buy"=~/b/ => 0
Mais("buy"=~/b/).to_boolean => false
Ne réfléchissez pas trop:
Alors,
Vous pouvez également ajouter ".downcase" si vous vous inquiétez des majuscules.
la source
nil.to_s == 'true' #false
la source
value.to_s == 'true' ? true : false
if true then true, if false then false
devinez quoi? Vous pouvez le supprimer complètement!value.to_s == 'true' ? true : false
devrait juste êtrevalue.to_s == 'true'
la source
Dans une application rails 5.1, j'utilise cette extension de base construite sur
ActiveRecord::Type::Boolean
. Cela fonctionne parfaitement pour moi lorsque je désérialise le booléen de la chaîne JSON.https://api.rubyonrails.org/classes/ActiveModel/Type/Boolean.html
initialiser les extensions principales
rspec
la source
Dans Rails, je préfère utiliser
ActiveModel::Type::Boolean.new.cast(value)
comme mentionné dans d'autres réponses iciMais quand j'écris en clair Ruby lib. alors j'utilise un hack où
JSON.parse
(bibliothèque Ruby standard) convertira la chaîne "true" entrue
et "false" enfalse
. Par exemple:Exemple d'application en direct:
la source
Travailler dans les rails 5
la source
ActiveModel::Type::Boolean.new.cast("False") # => true
... Utilisez to_s.downcase sur votre entrée est une bonne idéeJ'ai un petit hack pour celui-ci.
JSON.parse('false')
reviendrafalse
etJSON.parse('true')
retournera vrai. Mais cela ne fonctionne pas avecJSON.parse(true || false)
. Donc, si vous utilisez quelque chose commeJSON.parse(your_value.to_s)
ça, vous devriez atteindre votre objectif d'une manière simple mais hacky.la source
Un bijou comme https://rubygems.org/gems/to_bool peut être utilisé, mais il peut facilement être écrit sur une ligne en utilisant une expression régulière ou un ternaire.
exemple regex:
exemple ternaire:
L'avantage de la méthode regex est que les expressions régulières sont flexibles et peuvent correspondre à une grande variété de modèles. Par exemple, si vous pensez que var pourrait être l'un des "True", "False", "T", "F", "t" ou "f", vous pouvez modifier l'expression rationnelle:
la source
\A
/\z
est le début / la fin de la chaîne et^
/$
est le début / la fin de la ligne. Alors sivar == "true\nwhatevs"
alorsboolean == true
.var.eql?('true') ? true : false
beaucoup. Merci!Bien que j'aime l'approche de hachage (je l'ai utilisée dans le passé pour des choses similaires), étant donné que vous ne vous souciez vraiment que de la correspondance des valeurs de vérité - puisque - tout le reste est faux - vous pouvez vérifier l'inclusion dans un tableau:
ou si d'autres valeurs peuvent être considérées comme véridiques:
vous auriez à faire d'autres choses si votre original
value
pourrait être une casse mixte:mais encore une fois, pour votre description spécifique de votre problème, vous pourriez vous en tirer avec ce dernier exemple comme solution.
la source
Dans les rails, j'ai déjà fait quelque chose comme ceci:
Ce qui est bien si vous essayez de faire correspondre vos comparaisons de chaînes booléennes de la même manière que les rails le feraient pour votre base de données.
la source
Proche de ce qui est déjà posté, mais sans le paramètre redondant:
usage:
la source