【问题标题】:Why can't I "string".print()?为什么我不能“string”.print()?
【发布时间】:2012-09-04 23:59:30
【问题描述】:

我对 Python 和 Ruby(以及其他语言)中的 print() 的理解是它是一个字符串(或其他类型)的方法。因为它是如此常用的语法:

打印“嗨”

有效。

那么为什么 Python 中的 "hi".print() 或 Ruby 中的 "hi".print 不起作用?

【问题讨论】:

  • 如果你给一个字符串对象一个打印方法,你为什么会停在那里,那么系统中的每个对象都应该有一个打印方法。与切片、搜索等相比,打印确实不是一个特别像字符串的操作……打印只是 I/O 的一种特殊形式,你看不到像整数和字符串这样的对象,其写入方法需要一个文件句柄作为参数。
  • 当这个问题实际上是“为什么我不能输入随机的废话并让它运行”时,为什么会得到如此多的支持?这从什么时候变成了从完全无知开始接近一种语言?
  • @MatthewTrevor:放轻松。问题是关于什么成为方法以及什么成为全局函数等背后的逻辑。
  • 对这个问题的解释比我能处理的要宽泛得多。
  • @MatthewTrevor 考虑 echristopherson 的回答,我不认为这是一个愚蠢的问题。

标签: python ruby


【解决方案1】:

当您执行"hi".print() 之类的操作时,您是在暗示字符串对象"hi" 有一个方法print。不是这种情况。相反,print 是一个将字符串(或其他类型)作为输入的函数。

【讨论】:

  • 这只适用于 Python。 Ruby 没有函数,只有方法。在 Ruby 中,printIO 协议的一个方法,由例如IO#printStringIO#print 实现。另外,还有一个方便的方法Kernel#print,它基本上调用$>.print,其中$>是一个全局变量,表示默认输出IO流(通常$>指向STDOUT,但它没有至)。正是这种方便的方法让您可以只说print 'Hi' 而不是$>.print 'Hi'STDOUT.print 'Hi'
【解决方案2】:

Ruby 确实有一个方法 Object#display (doc here),它将对象的表示发送到当前输出流,或者指定为参数。

(如果我在行尾使用; 来抑制返回值的打印,我发现在irb 中很难使用;如果我这样做,display 的输出不会显示,即使我刷新流。)

【讨论】:

  • 竖起大拇指,因为我不知道Object#display,尽管我认为我不喜欢它的存在,因为任何给定的对象神奇地知道如何打印自己是没有意义的(因为:如何它应该看起来像吗?像 self.to_s 或 self.inspect 等,以及 b:它如何知道将自己打印到哪里?$stdout 或 $stderr 或一些随机文件或套接字或什么?每个对象的依赖关系多么糟糕需要了解流)
  • @Joshua Cheek:如果您不指定要输出到的流,它会使用伪全局 $> 的值,直到我查找它时我才知道它存在。
【解决方案3】:

不是字符串上的方法。在Python 3 之前,它是一个声明(就像breakimport),您可以同时使用print "hi"print("hi")。从 Python 3 开始,它是 replaced 通过 函数,因此您不能再使用 print "hi"

打印是一个函数

打印语句已替换为 print() 函数,用关键字参数替换大部分 旧打印语句的特殊语法 (PEP 3105)。

【讨论】:

    【解决方案4】:

    为什么它应该起作用?字符串类很少有 void print 方法——而且你永远不需要它们,因为标准的静态 print 函数无论如何都可以打印这些字符串。请务必注意:method(someObject)不一定someObject.method() 相同。

    【讨论】:

      【解决方案5】:

      你建议str.print应该做什么?

      打印到标准输出?标准错误怎么样?还是文件?还是串口?

      打印到标准输出确实是一种特殊情况,但它无处不在,有时会被忽视。

      那么我们每次创建字符串时都必须指定 str 应该打印到哪里?

      至少我们不得不说

      "foo".print(sys.stdout)
      

      希望这对你来说也很糟糕。这是职责的混淆

      【讨论】:

        【解决方案6】:

        print 不是 Python 中(或 Ruby 中,我相信)中字符串的方法。这是一个语句(在 Python 3 中它是一个全局函数)。为什么?一方面,并​​非您可以打印的所有内容都是字符串。 print 2呢?

        【讨论】:

        【解决方案7】:

        如果您更喜欢在 Ruby 中使用方法而不是语句,您可以使用方法显示 ("test".display) 来实现此目的或轻松定义新方法,例如

        class String
          def print
            puts self
          end
        end
        

        并像这样使用它

        "test".print
        

        【讨论】:

        • 像这样的猴子修补对象通常是一个坏习惯,尤其是在这种情况下,您正在创建大量依赖项。我知道在这种情况下它不会咬你,因为 print 在内核中,但这只是一个例外(可以写一整篇博客文章)。
        • 每个人都有权发表自己的意见,我认为这里没有任何依赖关系,除非您使用必须在代码中某处定义的方法
        • 依赖一个IO流和全局变量$stdout
        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2022-08-09
        • 1970-01-01
        • 2011-10-30
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2012-10-30
        相关资源
        最近更新 更多