如何将字段名称传递给方法并检查它们是否为空

时间:2018-03-22 20:45:19

标签: ruby-on-rails ruby

我想将一个对象(产品)和一个字段名称数组传递给一个方法,并查看该产品是否包含所有字段的数据。

作为辅助方法,我希望做一些像:

def show_card?(product, fields)
  # Check if any of the fields are blank. In this case:
  fields.each do |f|
    # product.name, product.details, product.color
    # Return false if all are blank.
    # Essentially how do I do: product.f.blank? (product.name.blank? in the first iteration)
  end
end

然后在部分

<% if show_card?(@product, ["name", "details", "color"]) %>
  # HTML 
<% end %>

4 个答案:

答案 0 :(得分:1)

Ruby约定是对方法,变量使用snake_case,并对模块和类使用CamelCase

def show_card?(product, fields)
  # Check if any of the fields are blank. In this case:
  fields.any?{|f| product.send(f.to_sym).empty?}
end

最好发送符号数组,因为它们是方法调用

<% if show_card?(@product, %i[name details color]) %>
  # HTML 
<% end %>

然后您不需要f.to_sym

在上一个方法中send(f)

答案 1 :(得分:0)

试试product.send(f).blank?。您需要学习.send()方法。

答案 2 :(得分:0)

怎么样:

product.attributes.slice(*fields).compact.length == fields.length

我想你也可以这样做:

(fields - product.attributes.slice(*fields).compact.keys).empty?

要将其分解,让我们说product.attributes返回:

{"id"=>1, "name"=>"Foo", "details"=>"Some Details", "color"=>nil, "created_at"=>Fri, 04 Aug 2017 22:42:43 UTC +00:00, "updated_at"=>Fri, 04 Aug 2017 22:42:43 UTC +00:00}

让我们说fields是:

["name", "details", "color"]

然后,product.attributes.slice(*fields)将返回:

{"name"=>"Foo", "details"=>"Some Details", "color"=>nil}

添加compact将返回:

{"name"=>"Foo", "details"=>"Some Details"}

从那里,您可以执行上述任一方法,只需跳过所有迭代业务。

顺便说一句,如果fields包含product上不存在的条目,那就没问题。比方说,fields是:

["name", "details", "color", "foo_bar"]

然后,product.attributes.slice(*fields).compact仍会返回:

{"name"=>"Foo", "details"=>"Some Details"}

上述任何一种方法仍会返回false

答案 3 :(得分:0)

另一种方法可能是

let frame = CGRect(origin: CGPoint(), size: spriteSize)

let sprite = UIView(frame: frame)
sprite.isHidden = true

let bottomLayer = CALayer()
bottomLayer.frame = frame
bottomLayer.contents = UIImage(named:"name1.png")!.cgImage
bottomLayer.transform = CATransform3DMakeScale(-1, 1, 1)
sprite.layer.addSublayer(bottomLayer)

let topLayer = CALayer()
topLayer.frame = frame
topLayer.contents = UIImage(named:"name2.png")!.cgImage
sprite.layer.addSublayer(topLayer)

parent.addSubview(sprite)

sprite.layer.position = fromPosition
sprite.isHidden = false

UIView.animate(withDuration: 3, delay: 0,
                    animations:{
    sprite.layer.transform =
            CATransform3DConcat(
                    CATransform3DMakeRotation(CGFloat.pi, 1, 0, 0))
    sprite.layer.position = targetPosition
})
如果您不了解安全导航操作符def show_card?(product, fields) fields.all? {|field| product&.field } end

this可能会有所帮助