【问题标题】:Ruby OOP correct concept?Ruby OOP 正确的概念?
【发布时间】:2016-04-25 08:37:39
【问题描述】:

下面的练习题是我的答案。

#Create a Tree class with a rings attribute and getter method.
#Trees create a ring for every winter that passes
#It should have a bear_fruit? method which should return true if the
#has fruit that year. the tree produces fruit when it has
#more than 7 rings but less than 15, but false otherwise.
#The class should also have an winter_season method that increases #rings attr by 1.

谁能就这段代码给我建设性的批评?

class Tree

  attr_accessor :winters, :rings, :bear_fruit?

  def initialize(winters, rings)
    @winters = winters
    @rings = rings   
  end

  def rings_created
    @winters = 0
    @rings = 0
    while @winters == @rings do
      @winters +=1
      @rings +=1
      break if @winters == 100  
    end 
  end
  end

  def bear_fruit
    if @rings > 6 || < 16
      @bear_fruit? = true
    else 
      @bear_fruit? = false   
    end
  end

 def winter_season
   @winters = 0
   @rings = 0
   while @winters < @rings do
     @winters +=1
     @rings +=2
     break if @winters == 100   
   end  
   end 
 end

end

【问题讨论】:

  • 打错了,我现在是凌晨 2 点......
  • 你不能创建像@bear_fruit?这样的实例变量。它们不能像方法名称那样包含?。您在这里的缩进也无处不在。为了清楚地看到正在发生的事情并识别错误,拥有组织良好、有序的代码很重要。请记住,解决这些问题的最佳方法是开发简单的单元测试来表达您的代码应该做什么,然后返回并让代码正常工作。这就是test driven development或TDD的原理。
  • 请努力正确格式化您的代码。其他读者也可能是凌晨 2 点 ;)
  • @margo 正要修复,但你打败了我。我保证在粘贴之前它看起来会更好;)
  • 你应该在提交之前修复它,这就是预览的目的。马上,任何人都可以从格式中看出这不会按原样工作。编程最重要的是让它工作,然后担心改进它。这可能看起来很苛刻,但如果你证明你已经做出了适当的努力,你会得到更多的帮助。

标签: ruby oop


【解决方案1】:

根据练习,你应该创建一个类Tree,它有一个属性rings和两个方法bear_fruit?winter_season

  • 创建一个Tree
    • rings 属性和 getter 方法
    • bear_fruit? 方法
      • 如果树有超过 7 个环但少于 15 个环,则返回 true
      • 否则返回false
    • winter_season 方法
      • rings 增加 1

就是这样。它没有说一棵树应该跟踪冬天,也没有提到任何循环。

这是我将如何实现它:

class Tree
  attr_reader :rings

  def initialize
    @rings = 0
  end

  def bear_fruit?
    @rings > 7 && @rings < 15
  end

  def winter_season
    @rings += 1
  end
end

【讨论】:

  • (8..14).include?(@rings) 更多地是 Rubyish 和英语。
  • @KeithBennett 你也可以写@rings.between?(8, 14),但这会导致代码和规范中的数字不同。 @rings &gt; 7 &amp;&amp; @rings &lt; 15 更接近于 “超过 7 但小于 15”,IMO。
  • 你说的是真的,但我认为偏离字面规范使用更人性化的符号是有价值的。 (而且,尽管数字不同,但条件是相同的。)我认为我们在 > &&
  • @KeithBennett 自然语言通常有点模棱两可。在不参考文档的情况下,尚不清楚 between? 是包含性的还是排他性的。另一方面,&lt; 在这方面是准确的。像 7 &lt; @rings &lt; 15 这样的链式表示法是完美的,但不幸的是,Ruby - 与 Python 不同 - 不支持这种语法。
  • 我知道您重视精确度,我对此表示赞赏。我的建议不是between,而是(8..14).include?(@rings)。假设一个人知道 Ruby 中某个范围的界限(我相信您知道它包括下限和上限,包括 2 个点,不包括 3 个点),它没有任何含糊之处。虽然这个单独的表达可能并不重要,但许多此类较低级别构造的积累 IMO 在理解一页代码时会产生更高的认知成本。我确实喜欢那种 Python 表示法,非常数学。
【解决方案2】:

首先,它有效吗?我猜不是。运行它,看看错误是什么。

Ruby 提供了多种循环方式,您可以在ruby docs 中查找这些方式。如果可以避免,我宁愿不使用 while 循环,部分原因是使用 break 会导致代码可读性降低。查找 times 方法和其他可枚举项。

【讨论】:

    猜你喜欢
    • 2016-09-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多