标签归档:multiline

正则表达式匹配多行文本块

问题:正则表达式匹配多行文本块

与跨多行的文本进行匹配时,让Python正则表达式无法正常工作有点麻烦。示例文本为(“ \ n”是换行符)

some Varying TEXT\n
\n
DSJFKDAFJKDAFJDSAKFJADSFLKDLAFKDSAF\n
[more of the above, ending with a newline]\n
[yep, there is a variable number of lines here]\n
\n
(repeat the above a few hundred times).

我想捕获两件事:“ some_Varying_TEXT”部分,以及一次捕获中位于其下方两行的所有大写文本行(我以后可以去除换行符)。我尝试了几种方法:

re.compile(r"^>(\w+)$$([.$]+)^$", re.MULTILINE) # try to capture both parts
re.compile(r"(^[^>][\w\s]+)$", re.MULTILINE|re.DOTALL) # just textlines

并有很多变化,没有运气。最后一个似乎与文本行一一对应,这不是我真正想要的。我可以抓住第一部分,没问题,但是我似乎无法抓住4-5行的大写文本。我希望match.group(1)是some_Varying_Text,而group(2)是line1 + line2 + line3 + etc,直到遇到空行。

如果有人好奇,它应该是构成蛋白质的氨基酸序列。

I’m having a bit of trouble getting a Python regex to work when matching against text that spans multiple lines. The example text is (‘\n’ is a newline)

some Varying TEXT\n
\n
DSJFKDAFJKDAFJDSAKFJADSFLKDLAFKDSAF\n
[more of the above, ending with a newline]\n
[yep, there is a variable number of lines here]\n
\n
(repeat the above a few hundred times).

I’d like to capture two things: the ‘some_Varying_TEXT’ part, and all of the lines of uppercase text that comes two lines below it in one capture (i can strip out the newline characters later). I’ve tried with a few approaches:

re.compile(r"^>(\w+)$$([.$]+)^$", re.MULTILINE) # try to capture both parts
re.compile(r"(^[^>][\w\s]+)$", re.MULTILINE|re.DOTALL) # just textlines

and a lot of variations hereof with no luck. The last one seems to match the lines of text one by one, which is not what I really want. I can catch the first part, no problem, but I can’t seem to catch the 4-5 lines of uppercase text. I’d like match.group(1) to be some_Varying_Text and group(2) to be line1+line2+line3+etc until the empty line is encountered.

If anyone’s curious, its supposed to be a sequence of aminoacids that make up a protein.


回答 0

试试这个:

re.compile(r"^(.+)\n((?:\n.+)+)", re.MULTILINE)

我认为您的最大问题是,您期望^$定位符匹配换行符,但它们不匹配。在多行模式,^匹配立即位置以下换行符和$立即位置相匹配一个换行符。

同样要注意,换行符可以由换行符(\ n),回车符(\ r)或回车符+换行符(\ r \ n)组成。如果不确定目标文本仅使用换行符,则应使用此更广泛的正则表达式版本:

re.compile(r"^(.+)(?:\n|\r\n?)((?:(?:\n|\r\n?).+)+)", re.MULTILINE)

顺便说一句,您不想在这里使用DOTALL修饰符;您依赖点与换行符以外的所有内容都匹配的事实。

Try this:

re.compile(r"^(.+)\n((?:\n.+)+)", re.MULTILINE)

I think your biggest problem is that you’re expecting the ^ and $ anchors to match linefeeds, but they don’t. In multiline mode, ^ matches the position immediately following a newline and $ matches the position immediately preceding a newline.

Be aware, too, that a newline can consist of a linefeed (\n), a carriage-return (\r), or a carriage-return+linefeed (\r\n). If you aren’t certain that your target text uses only linefeeds, you should use this more inclusive version of the regex:

re.compile(r"^(.+)(?:\n|\r\n?)((?:(?:\n|\r\n?).+)+)", re.MULTILINE)

BTW, you don’t want to use the DOTALL modifier here; you’re relying on the fact that the dot matches everything except newlines.


回答 1

这将起作用:

>>> import re
>>> rx_sequence=re.compile(r"^(.+?)\n\n((?:[A-Z]+\n)+)",re.MULTILINE)
>>> rx_blanks=re.compile(r"\W+") # to remove blanks and newlines
>>> text="""Some varying text1
...
... AAABBBBBBCCCCCCDDDDDDD
... EEEEEEEFFFFFFFFGGGGGGG
... HHHHHHIIIIIJJJJJJJKKKK
...
... Some varying text 2
...
... LLLLLMMMMMMNNNNNNNOOOO
... PPPPPPPQQQQQQRRRRRRSSS
... TTTTTUUUUUVVVVVVWWWWWW
... """
>>> for match in rx_sequence.finditer(text):
...   title, sequence = match.groups()
...   title = title.strip()
...   sequence = rx_blanks.sub("",sequence)
...   print "Title:",title
...   print "Sequence:",sequence
...   print
...
Title: Some varying text1
Sequence: AAABBBBBBCCCCCCDDDDDDDEEEEEEEFFFFFFFFGGGGGGGHHHHHHIIIIIJJJJJJJKKKK

Title: Some varying text 2
Sequence: LLLLLMMMMMMNNNNNNNOOOOPPPPPPPQQQQQQRRRRRRSSSTTTTTUUUUUVVVVVVWWWWWW

关于此正则表达式的一些解释可能会有用: ^(.+?)\n\n((?:[A-Z]+\n)+)

  • 第一个字符(^)表示“从行首开始”。请注意,它与换行符本身不匹配(与$相同:表示“仅在换行符之前”,但与换行符本身不匹配)。
  • 然后(.+?)\n\n表示“匹配尽可能少的字符(允许所有字符),直到到达两个换行符”。结果(没有换行符)放在第一组中。
  • [A-Z]+\n意思是“匹配尽可能多的大写字母,直到到达换行符为止。这定义了我称之为文本行
  • ((?:文本行)+)表示匹配一个或多个文本行,但不要将每一行都放在一组中。相反,把所有文本行中的一组。
  • \n如果要在末尾强制使用双换行符,则可以在正则表达式中添加final 。
  • 另外,如果你不知道你会得到什么类型的换行符(\n\r\r\n),那么仅仅通过替换每次出现解决了正则表达式\n(?:\n|\r\n?)

This will work:

>>> import re
>>> rx_sequence=re.compile(r"^(.+?)\n\n((?:[A-Z]+\n)+)",re.MULTILINE)
>>> rx_blanks=re.compile(r"\W+") # to remove blanks and newlines
>>> text="""Some varying text1
...
... AAABBBBBBCCCCCCDDDDDDD
... EEEEEEEFFFFFFFFGGGGGGG
... HHHHHHIIIIIJJJJJJJKKKK
...
... Some varying text 2
...
... LLLLLMMMMMMNNNNNNNOOOO
... PPPPPPPQQQQQQRRRRRRSSS
... TTTTTUUUUUVVVVVVWWWWWW
... """
>>> for match in rx_sequence.finditer(text):
...   title, sequence = match.groups()
...   title = title.strip()
...   sequence = rx_blanks.sub("",sequence)
...   print "Title:",title
...   print "Sequence:",sequence
...   print
...
Title: Some varying text1
Sequence: AAABBBBBBCCCCCCDDDDDDDEEEEEEEFFFFFFFFGGGGGGGHHHHHHIIIIIJJJJJJJKKKK

Title: Some varying text 2
Sequence: LLLLLMMMMMMNNNNNNNOOOOPPPPPPPQQQQQQRRRRRRSSSTTTTTUUUUUVVVVVVWWWWWW

Some explanation about this regular expression might be useful: ^(.+?)\n\n((?:[A-Z]+\n)+)

  • The first character (^) means “starting at the beginning of a line”. Be aware that it does not match the newline itself (same for $: it means “just before a newline”, but it does not match the newline itself).
  • Then (.+?)\n\n means “match as few characters as possible (all characters are allowed) until you reach two newlines”. The result (without the newlines) is put in the first group.
  • [A-Z]+\n means “match as many upper case letters as possible until you reach a newline. This defines what I will call a textline.
  • ((?:textline)+) means match one or more textlines but do not put each line in a group. Instead, put all the textlines in one group.
  • You could add a final \n in the regular expression if you want to enforce a double newline at the end.
  • Also, if you are not sure about what type of newline you will get (\n or \r or \r\n) then just fix the regular expression by replacing every occurrence of \n by (?:\n|\r\n?).

回答 2

如果每个文件只有一个氨基酸序列,我将完全不使用正则表达式。就像这样:

def read_amino_acid_sequence(path):
    with open(path) as sequence_file:
        title = sequence_file.readline() # read 1st line
        aminoacid_sequence = sequence_file.read() # read the rest

    # some cleanup, if necessary
    title = title.strip() # remove trailing white spaces and newline
    aminoacid_sequence = aminoacid_sequence.replace(" ","").replace("\n","")
    return title, aminoacid_sequence

If each file only has one sequence of aminoacids, I wouldn’t use regular expressions at all. Just something like this:

def read_amino_acid_sequence(path):
    with open(path) as sequence_file:
        title = sequence_file.readline() # read 1st line
        aminoacid_sequence = sequence_file.read() # read the rest

    # some cleanup, if necessary
    title = title.strip() # remove trailing white spaces and newline
    aminoacid_sequence = aminoacid_sequence.replace(" ","").replace("\n","")
    return title, aminoacid_sequence

回答 3

找:

^>([^\n\r]+)[\n\r]([A-Z\n\r]+)

\ 1 = some_varying_text

\ 2 =所有CAPS的行

编辑(证明这可行):

text = """> some_Varying_TEXT

DSJFKDAFJKDAFJDSAKFJADSFLKDLAFKDSAF
GATACAACATAGGATACA
GGGGGAAAAAAAATTTTTTTTT
CCCCAAAA

> some_Varying_TEXT2

DJASDFHKJFHKSDHF
HHASGDFTERYTERE
GAGAGAGAGAG
PPPPPAAAAAAAAAAAAAAAP
"""

import re

regex = re.compile(r'^>([^\n\r]+)[\n\r]([A-Z\n\r]+)', re.MULTILINE)
matches = [m.groups() for m in regex.finditer(text)]

for m in matches:
    print 'Name: %s\nSequence:%s' % (m[0], m[1])

find:

^>([^\n\r]+)[\n\r]([A-Z\n\r]+)

\1 = some_varying_text

\2 = lines of all CAPS

Edit (proof that this works):

text = """> some_Varying_TEXT

DSJFKDAFJKDAFJDSAKFJADSFLKDLAFKDSAF
GATACAACATAGGATACA
GGGGGAAAAAAAATTTTTTTTT
CCCCAAAA

> some_Varying_TEXT2

DJASDFHKJFHKSDHF
HHASGDFTERYTERE
GAGAGAGAGAG
PPPPPAAAAAAAAAAAAAAAP
"""

import re

regex = re.compile(r'^>([^\n\r]+)[\n\r]([A-Z\n\r]+)', re.MULTILINE)
matches = [m.groups() for m in regex.finditer(text)]

for m in matches:
    print 'Name: %s\nSequence:%s' % (m[0], m[1])

回答 4

以下是匹配多行文本块的正则表达式:

import re
result = re.findall('(startText)(.+)((?:\n.+)+)(endText)',input)

The following is a regular expression matching a multiline block of text:

import re
result = re.findall('(startText)(.+)((?:\n.+)+)(endText)',input)

回答 5

我的偏爱。

lineIter= iter(aFile)
for line in lineIter:
    if line.startswith( ">" ):
         someVaryingText= line
         break
assert len( lineIter.next().strip() ) == 0
acids= []
for line in lineIter:
    if len(line.strip()) == 0:
        break
    acids.append( line )

此时,您将someVaryingText作为字符串,并将酸作为字符串列表。您可以"".join( acids )制作一个字符串。

我发现它比多行正则表达式更令人沮丧(并且更灵活)。

My preference.

lineIter= iter(aFile)
for line in lineIter:
    if line.startswith( ">" ):
         someVaryingText= line
         break
assert len( lineIter.next().strip() ) == 0
acids= []
for line in lineIter:
    if len(line.strip()) == 0:
        break
    acids.append( line )

At this point you have someVaryingText as a string, and the acids as a list of strings. You can do "".join( acids ) to make a single string.

I find this less frustrating (and more flexible) than multiline regexes.


在Python中格式化多行字典的正确方法是什么?

问题:在Python中格式化多行字典的正确方法是什么?

在Python中,我想在代码中编写多行字典。有几种方法可以格式化它。我想到的是一些:

  1. mydict = { "key1": 1,
               "key2": 2,
               "key3": 3, }
  2. mydict = { "key1": 1,
               "key2": 2,
               "key3": 3,
             }
  3. mydict = {
        "key1": 1,
        "key2": 2,
        "key3": 3,
    }

我知道以上任何一种在语法上都是正确的,但是我假设Python字典有一种首选的缩进和换行样式。它是什么?

注意:这不是语法问题。就我所知,以上所有都是有效的Python语句,并且彼此等效。

In Python, I want to write a multi-line dict in my code. There are a couple of ways one could format it. Here are a few that I could think of:

  1. mydict = { "key1": 1,
               "key2": 2,
               "key3": 3, }
    
  2. mydict = { "key1": 1,
               "key2": 2,
               "key3": 3,
             }
    
  3. mydict = {
        "key1": 1,
        "key2": 2,
        "key3": 3,
    }
    

I know that any of the above is syntactically correct, but I assume that there is one preferred indentation and line-break style for Python dicts. What is it?

Note: This is not an issue of syntax. All of the above are (as far as I know) valid Python statements and are equivalent to each other.


回答 0

我使用#3。长列表,元组等也是如此。不需要在缩进之外添加任何额外的空格。一如既往,保持一致。

mydict = {
    "key1": 1,
    "key2": 2,
    "key3": 3,
}

mylist = [
    (1, 'hello'),
    (2, 'world'),
]

nested = {
    a: [
        (1, 'a'),
        (2, 'b'),
    ],
    b: [
        (3, 'c'),
        (4, 'd'),
    ],
}

同样,这是在不引入任何空格的情况下包括大字符串的我的首选方式(例如,如果使用三引号的多行字符串,则会得到此信息):

data = (
    "iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAABG"
    "l0RVh0U29mdHdhcmUAQWRvYmUgSW1hZ2VSZWFkeXHJZTwAAAEN"
    "xBRpFYmctaKCfwrBSCrRLuL3iEW6+EEUG8XvIVjYWNgJdhFjIX"
    "rz6pKtPB5e5rmq7tmxk+hqO34e1or0yXTGrj9sXGs1Ib73efh1"
    "AAAABJRU5ErkJggg=="
)

I use #3. Same for long lists, tuples, etc. It doesn’t require adding any extra spaces beyond the indentations. As always, be consistent.

mydict = {
    "key1": 1,
    "key2": 2,
    "key3": 3,
}

mylist = [
    (1, 'hello'),
    (2, 'world'),
]

nested = {
    a: [
        (1, 'a'),
        (2, 'b'),
    ],
    b: [
        (3, 'c'),
        (4, 'd'),
    ],
}

Similarly, here’s my preferred way of including large strings without introducing any whitespace (like you’d get if you used triple-quoted multi-line strings):

data = (
    "iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAABG"
    "l0RVh0U29mdHdhcmUAQWRvYmUgSW1hZ2VSZWFkeXHJZTwAAAEN"
    "xBRpFYmctaKCfwrBSCrRLuL3iEW6+EEUG8XvIVjYWNgJdhFjIX"
    "rz6pKtPB5e5rmq7tmxk+hqO34e1or0yXTGrj9sXGs1Ib73efh1"
    "AAAABJRU5ErkJggg=="
)

回答 1

首先,就像史蒂文·鲁姆巴尔斯基(Steven Rumbalski)所说的那样,“ PEP8不能解决这个问题”,因此这是个人喜好问题。

我将使用与您的格式3类似但不完全相同的格式。这是我的,以及原因。

my_dictionary = { # Don't think dict(...) notation has more readability
    "key1": 1, # Indent by one press of TAB (i.e. 4 spaces)
    "key2": 2, # Same indentation scale as above
    "key3": 3, # Keep this final comma, so that future addition won't show up as 2-lines change in code diff
    } # My favorite: SAME indentation AS ABOVE, to emphasize this bracket is still part of the above code block!
the_next_line_of_code() # Otherwise the previous line would look like the begin of this part of code

bad_example = {
               "foo": "bar", # Don't do this. Unnecessary indentation wastes screen space
               "hello": "world" # Don't do this. Omitting the comma is not good.
} # You see? This line visually "joins" the next line when in a glance
the_next_line_of_code()

btw_this_is_a_function_with_long_name_or_with_lots_of_parameters(
    foo='hello world',  # So I put one parameter per line
    bar=123,  # And yeah, this extra comma here is harmless too;
              # I bet not many people knew/tried this.
              # Oh did I just show you how to write
              # multiple-line inline comment here?
              # Basically, same indentation forms a natural paragraph.
    ) # Indentation here. Same idea as the long dict case.
the_next_line_of_code()

# By the way, now you see how I prefer inline comment to document the very line.
# I think this inline style is more compact.
# Otherwise you will need extra blank line to split the comment and its code from others.

some_normal_code()

# hi this function is blah blah
some_code_need_extra_explanation()

some_normal_code()

First of all, like Steven Rumbalski said, “PEP8 doesn’t address this question”, so it is a matter of personal preference.

I would use a similar but not identical format as your format 3. Here is mine, and why.

my_dictionary = { # Don't think dict(...) notation has more readability
    "key1": 1, # Indent by one press of TAB (i.e. 4 spaces)
    "key2": 2, # Same indentation scale as above
    "key3": 3, # Keep this final comma, so that future addition won't show up as 2-lines change in code diff
    } # My favorite: SAME indentation AS ABOVE, to emphasize this bracket is still part of the above code block!
the_next_line_of_code() # Otherwise the previous line would look like the begin of this part of code

bad_example = {
               "foo": "bar", # Don't do this. Unnecessary indentation wastes screen space
               "hello": "world" # Don't do this. Omitting the comma is not good.
} # You see? This line visually "joins" the next line when in a glance
the_next_line_of_code()

btw_this_is_a_function_with_long_name_or_with_lots_of_parameters(
    foo='hello world',  # So I put one parameter per line
    bar=123,  # And yeah, this extra comma here is harmless too;
              # I bet not many people knew/tried this.
              # Oh did I just show you how to write
              # multiple-line inline comment here?
              # Basically, same indentation forms a natural paragraph.
    ) # Indentation here. Same idea as the long dict case.
the_next_line_of_code()

# By the way, now you see how I prefer inline comment to document the very line.
# I think this inline style is more compact.
# Otherwise you will need extra blank line to split the comment and its code from others.

some_normal_code()

# hi this function is blah blah
some_code_need_extra_explanation()

some_normal_code()

回答 2

由于您的键是字符串,并且因为我们在谈论可读性,所以我更喜欢:

mydict = dict(
    key1 = 1,
    key2 = 2,
    key3 = 3,
)

Since your keys are strings and since we are talking about readability, I prefer :

mydict = dict(
    key1 = 1,
    key2 = 2,
    key3 = 3,
)

回答 3

通常,如果您有大型python对象,则很难格式化它们。我个人更喜欢为此使用一些工具。

这是python-beautifier-www.cleancss.com/python-beautify,可立即将您的数据转换为可自定义的样式。

Usually, if you have big python objects it’s quite hard to format them. I personally prefer using some tools for that.

Here is python-beautifier – www.cleancss.com/python-beautify that instantly turns your data into customizable style.


回答 4

dict(rank = int(lst[0]),
                grade = str(lst[1]),
                channel=str(lst[2])),
                videos = float(lst[3].replace(",", " ")),
                subscribers = float(lst[4].replace(",", "")),
                views = float(lst[5].replace(",", "")))
dict(rank = int(lst[0]),
                grade = str(lst[1]),
                channel=str(lst[2])),
                videos = float(lst[3].replace(",", " ")),
                subscribers = float(lst[4].replace(",", "")),
                views = float(lst[5].replace(",", "")))

回答 5

根据我在教程和其他方面的经验,似乎总是首选2号,但这是个人喜好选择,而不是其他任何事情。

From my experience with tutorials, and other things number 2 always seems preferred, but it’s a personal preference choice more than anything else.


回答 6

通常,您不会在最后一个输入项后加入逗号,但Python会为您更正。

Generally, you would not include the comma after the final entry, but Python will correct that for you.


为什么Python没有多行注释?

问题:为什么Python没有多行注释?

好的,我知道三引号字符串可以用作多行注释。例如,

"""Hello, I am a 
   multiline comment"""

'''Hello, I am a 
   multiline comment'''

但是从技术上讲,这些是字符串,对吗?

我已经在Google上搜索并阅读了Python样式指南,但是无法找到关于为什么没有正式实现多行,/ * * /注释类型的技术答案。我使用三重引号没有问题,但是我对导致这个设计决定的原因有点好奇。

OK, I’m aware that triple-quotes strings can serve as multiline comments. For example,

"""Hello, I am a 
   multiline comment"""

and

'''Hello, I am a 
   multiline comment'''

But technically speaking these are strings, correct?

I’ve googled and read the Python style guide, but I was unable to find a technical answer to why there is no formal implementation of multiline, /* */ type of comments. I have no problem using triple quotes, but I am a little curious as to what led to this design decision.


回答 0

我怀疑您会得到比“ Guido不需要多行注释”更好的答案。

Guido在推特上发布了以下内容:

Python提示:您可以将多行字符串用作多行注释。除非用作文档字符串,否则它们不会生成任何代码!:-)

I doubt you’ll get a better answer than, “Guido didn’t feel the need for multi-line comments”.

Guido has tweeted about this:

Python tip: You can use multi-line strings as multi-line comments. Unless used as docstrings, they generate no code! :-)


回答 1

多行注释很容易被破坏。如果您在一个简单的计算器程序中拥有以下内容,该怎么办?

operation = ''
print("Pick an operation:  +-*/")
# Get user input here

尝试用多行注释对此进行注释:

/*
operation = ''
print("Pick an operation:  +-*/")
# Get user input here
*/

糟糕,您的字符串包含结尾注释定界符。

Multi-line comments are easily breakable. What if you have the following in a simple calculator program?

operation = ''
print("Pick an operation:  +-*/")
# Get user input here

Try to comment that with a multi-line comment:

/*
operation = ''
print("Pick an operation:  +-*/")
# Get user input here
*/

Oops, your string contains the end comment delimiter.


回答 2

用三引号括起来的文本不应视为多行注释;按照惯例,它们是docstrings。他们应该描述您的代码做什么以及如何使用它,而不是描述诸如注释代码块之类的内容。

根据Guido的说法,Python中的多行注释只是连续的单行注释(搜索“块注释”)。

为了注释代码块,我有时使用以下模式:

if False:
    # A bunch of code

Triple-quoted text should NOT be considered multi-line comments; by convention, they are docstrings. They should describe what your code does and how to use it, but not for things like commenting out blocks of code.

According to Guido, multiline comments in Python are just contiguous single-line comments (search for “block comments”).

To comment blocks of code, I sometimes use the following pattern:

if False:
    # A bunch of code

回答 3

这可能回到核心概念,即应该有一种显而易见的方法来完成一项任务。其他注释样式会增加不必要的复杂性,并可能降低可读性。

This likely goes back to the core concept that there should be one obvious way to do a task. Additional comment styles add unnecessary complications and could decrease readability.


回答 4

好吧,三引号用作文档字符串中的多行注释。#注释用作内联注释,人们逐渐习惯了。

大多数脚本语言也没有多行注释。也许是原因所在?

参见PEP 0008注释部分

并查看您的Python编辑器是否提供了一些用于块注释的键盘快捷键。Emacs以及Eclipse都支持它,大概大多数体面的IDE都支持。

Well, the triple-quotes are used as multiline comments in docstrings. And # comments are used as inline comments and people get use to it.

Most of script languages don’t have multiline comments either. Maybe that’s the cause?

See PEP 0008, section Comments

And see if your Python editor offers some keyboard shortcut for block commenting. Emacs supports it, as well as Eclipse, presumably most of decent IDEs does.


回答 5

Python的禅宗

应该有一种-最好只有一种-显而易见的方法。

From The Zen of Python:

There should be one– and preferably only one –obvious way to do it.


回答 6

就我个人而言,Java的评论风格就像

/*
 * My multi-line comment in Java
 */

因此,如果您的样式是前面示例的典型样式,那么仅具有单行注释并不是一件坏事,因为相比之下,您将拥有

#
# My multi-line comment in Python
#

VB.NET也是一种仅具有单行注释的语言,我个人认为它很烦人,因为注释最终看起来不像注释,而更像某种引用

'
' This is a VB.NET example
'

仅单行注释最终会比多行注释具有更少的字符使用率,并且在正则表达式语句中不太可能被某些狡猾的字符转义?不过,我倾向于同意内德。

Personally my comment style in say Java is like

/*
 * My multi-line comment in Java
 */

So having single-line only comments isn’t such a bad thing if your style is typical to the preceding example because in comparison you’d have

#
# My multi-line comment in Python
#

VB.NET is also a language with single-line only commenting, and personally I find it annoying as comments end up looking less likes comments and more like some kind of quote

'
' This is a VB.NET example
'

Single-line-only comments end up having less character-usage than multi-line comments, and are less likely to be escaped by some dodgy characters in a regex statement perhaps? I’d tend to agree with Ned though.


回答 7

Pycharm IDE中注释掉一段代码:

  • 代码 带线注释
  • Windows或Linux:Ctrl+/
  • Mac OS:Command+/

To comment out a block of code in the Pycharm IDE:

  • Code | Comment with Line Comment
  • Windows or Linux: Ctrl + /
  • Mac OS: Command + /

回答 8

# This
# is
# a 
# multi-line
# comment

使用注释块或在编辑器中搜索并替换(s / ^ /#/ g)即可实现此目的。

# This
# is
# a 
# multi-line
# comment

Use comment block or search and replace (s/^/#/g) in your editor to achieve this.


回答 9

我通过为文本编辑器(TextPad)下载宏解决了这一问题,该宏使我可以突出显示行,然后在每行的第一行插入#。类似的宏将删除#。有人可能会问为什么需要多行,但是当您尝试“关闭”代码块以进行调试时,它会派上用场。

I solved this by downloading a macro for my text editor (TextPad) that lets me highlight lines and it then inserts # at the first of each line. A similar macro removes the #’s. Some may ask why multiline is necessary but it comes in handy when you’re trying to “turn off” a block of code for debugging purposes.


回答 10

对于在Python中寻找多行注释的其他人-使用三引号格式可能会产生一些问题,因为我刚刚学到了很难的方法。考虑一下:

this_dict = {
    'name': 'Bob',

"""
This is a multiline comment in the middle of a dictionary
"""

    'species': 'Cat'
}

多行注释将被塞入下一个字符串中,从而弄乱了 'species'密钥。最好仅#用于评论。

For anyone else looking for multi-line comments in Python – using the triple quote format can have some problematic consequences, as I’ve just learned the hard way. Consider this:

this_dict = {
    'name': 'Bob',

"""
This is a multiline comment in the middle of a dictionary
"""

    'species': 'Cat'
}

The multi-line comment will be tucked into the next string, messing up the 'species' key. Better to just use # for comments.


回答 11

因为#约定是常见的约定,所以对于多行注释,您实际上无能为力,而对#符号注释则无能为力。这是历史性的意外,就像/* ... */回溯到PL / I 的评论之初一样,

Because the # convention is a common one, and there really isn’t anything you can do with a multiline comment that you can’t with a #-sign comment. It’s a historical accident, like the ancestry of /* ... */ comments going back to PL/I,


回答 12

假设只是认为它们是不必要的。由于键入非常容易,因此#a comment多行注释只能包含许多单行注释。

另一方面,对于HTML,更需要多行。很难继续打字<!--comments like this-->

Assume that they were just considered unnecessary. Since it’s so easy to just type #a comment, multiline comments can just consist of many single line comments.

For HTML, on the other hand, there’s more of a need for multiliners. It’s harder to keep typing <!--comments like this-->.


回答 13

这只是一个猜测..但是

因为它们是字符串,所以它们具有一些语义值(编译器不会摆脱它们),因此将它们用作文档字符串是有意义的。它们实际上成为AST的一部分,因此提取文档变得更加容易。

This is just a guess .. but

Because they are strings, they have some semantic value (the compiler doesn’t get rid of them), therefore it makes sense for them to be used as docstrings. They actually become part of the AST, so extracting documentation becomes easier.


回答 14

此外,多行注释是一个bit子。抱歉地说,但是不管使用哪种语言,我都不会将它们用于调试目的。假设您有这样的代码:

void someFunction()
{
    Something
    /*Some comments*/
    Something else
}

然后,您会发现代码中有些内容无法使用调试器进行修复,因此您可以通过使用多行注释注释掉越来越小的代码块来开始手动调试它。然后将提供以下功能:

void someFunction()
{ /*
    Something
   /* Comments */
   Something more*/
}

这真令人讨厌。

Besides, multiline comments are a bitch. Sorry to say, but regardless of the language, I don’t use them for anything else than debugging purposes. Say you have code like this:

void someFunction()
{
    Something
    /*Some comments*/
    Something else
}

Then you find out that there is something in your code you can’t fix with the debugger, so you start manually debugging it by commenting out smaller and smaller chuncks of code with theese multiline comments. This would then give the function:

void someFunction()
{ /*
    Something
   /* Comments */
   Something more*/
}

This is really irritating.


回答 15

使用IDLE的多行注释:

  • Mac OS X中,后选码,注释与代码块Ctrl+ 3并取消使用Ctrl+ 4

  • Windows,选择代码后,用Ctrl+ Alt+ 注释一段代码,3然后使用Ctrl+ At+ 取消注释4

Multiline comments using IDLE on:

  • Mac OS X, after code selection, comment a block of code with Ctrl+3 and uncomment using Ctrl+4.

  • Windows, after code selection, comment a block of code with Ctrl+Alt+3 and uncomment using Ctrl+At+4.


回答 16

我记得读过一篇关于将多行注释放入三引号中的变量的家伙的文章:

x = '''
This is my
super-long mega-comment.
Wow there are a lot of lines
going on here!
'''

这确实占用了一些内存,但是它为您提供了多行注释功能,并且大多数编辑器都会为您突出显示语法:)

通过简单地将其包装起来,注释掉代码也很容易

x = '''

'''

I remember reading about one guy who would put his multi-line comments into a triple-quoted variable:

x = '''
This is my
super-long mega-comment.
Wow there are a lot of lines
going on here!
'''

This does take up a bit of memory, but it gives you multi-line comment functionality, and plus most editors will highlight the syntax for you :)

It’s also easy to comment out code by simply wrapping it with

x = '''

and

'''

创建长的多行字符串的Pythonic方法

问题:创建长的多行字符串的Pythonic方法

我有一个很长的查询。我想在Python中将其分成几行。用JavaScript做到这一点的一种方法是使用几个句子,然后将它们与一个+运算符连接起来(我知道,这可能不是最有效的方法,但是我并不真正关心此阶段的性能,只是代码可读性) 。例:

var long_string = 'some text not important. just garbage to' +
                  'illustrate my example';

我尝试在Python中做类似的事情,但是没有用,所以我过去常常\拆分长字符串。但是,我不确定这是否是唯一/最佳/最佳的方法。看起来很尴尬。实际代码:

query = 'SELECT action.descr as "action", '\
    'role.id as role_id,'\
    'role.descr as role'\
    'FROM '\
    'public.role_action_def,'\
    'public.role,'\
    'public.record_def, '\
    'public.action'\
    'WHERE role.id = role_action_def.role_id AND'\
    'record_def.id = role_action_def.def_id AND'\
    'action.id = role_action_def.action_id AND'\
    'role_action_def.account_id = ' + account_id + ' AND'\
    'record_def.account_id=' + account_id + ' AND'\
    'def_id=' + def_id

I have a very long query. I would like to split it in several lines in Python. A way to do it in JavaScript would be using several sentences and joining them with a + operator (I know, maybe it’s not the most efficient way to do it, but I’m not really concerned about performance in this stage, just code readability). Example:

var long_string = 'some text not important. just garbage to' +
                  'illustrate my example';

I tried doing something similar in Python, but it didn’t work, so I used \ to split the long string. However, I’m not sure if this is the only/best/pythonicest way of doing it. It looks awkward. Actual code:

query = 'SELECT action.descr as "action", '\
    'role.id as role_id,'\
    'role.descr as role'\
    'FROM '\
    'public.role_action_def,'\
    'public.role,'\
    'public.record_def, '\
    'public.action'\
    'WHERE role.id = role_action_def.role_id AND'\
    'record_def.id = role_action_def.def_id AND'\
    'action.id = role_action_def.action_id AND'\
    'role_action_def.account_id = ' + account_id + ' AND'\
    'record_def.account_id=' + account_id + ' AND'\
    'def_id=' + def_id

回答 0

您在谈论多行字符串吗?容易,使用三引号将它们开始和结束。

s = """ this is a very
        long string if I had the
        energy to type more and more ..."""

您也可以使用单引号(当然在开始和结束时使用三个引号),并将结果字符串s与其他任何字符串一样对待。

注意:与任何字符串一样,引号和结尾引号之间的任何内容都将成为字符串的一部分,因此本示例中有一个前导空格(如@ root45所指出)。该字符串还将包含空格和换行符。

即:

' this is a very\n        long string if I had the\n        energy to type more and more ...'

最后,还可以像这样在Python中构造长行:

 s = ("this is a very"
      "long string too"
      "for sure ..."
     )

其中将包含任何额外的空格或换行符(这是一个有意的示例,显示了跳过空格的结果将导致什么):

'this is a verylong string toofor sure ...'

不需要逗号,只需将要连接的字符串放在一对括号中,并确保考虑到任何需要的空格和换行符。

Are you talking about multi-line strings? Easy, use triple quotes to start and end them.

s = """ this is a very
        long string if I had the
        energy to type more and more ..."""

You can use single quotes too (3 of them of course at start and end) and treat the resulting string s just like any other string.

NOTE: Just as with any string, anything between the starting and ending quotes becomes part of the string, so this example has a leading blank (as pointed out by @root45). This string will also contain both blanks and newlines.

I.e.,:

' this is a very\n        long string if I had the\n        energy to type more and more ...'

Finally, one can also construct long lines in Python like this:

 s = ("this is a very"
      "long string too"
      "for sure ..."
     )

which will not include any extra blanks or newlines (this is a deliberate example showing what the effect of skipping blanks will result in):

'this is a verylong string toofor sure ...'

No commas required, simply place the strings to be joined together into a pair of parenthesis and be sure to account for any needed blanks and newlines.


回答 1

如果您不希望使用多行字符串,而只需要一个长的单行字符串,则可以使用括号,只需确保在字符串段之间不包含逗号,那么它将是一个元组。

query = ('SELECT   action.descr as "action", '
         'role.id as role_id,'
         'role.descr as role'
         ' FROM '
         'public.role_action_def,'
         'public.role,'
         'public.record_def, '
         'public.action'
         ' WHERE role.id = role_action_def.role_id AND'
         ' record_def.id = role_action_def.def_id AND'
         ' action.id = role_action_def.action_id AND'
         ' role_action_def.account_id = '+account_id+' AND'
         ' record_def.account_id='+account_id+' AND'
         ' def_id='+def_id)

在您正在构造的SQL语句中,多行字符串也可以。但是,如果多行字符串将包含额外的空格将是一个问题,那么这将是实现所需内容的好方法。

If you don’t want a multiline string but just have a long single line string, you can use parentheses, just make sure you don’t include commas between the string segments, then it will be a tuple.

query = ('SELECT   action.descr as "action", '
         'role.id as role_id,'
         'role.descr as role'
         ' FROM '
         'public.role_action_def,'
         'public.role,'
         'public.record_def, '
         'public.action'
         ' WHERE role.id = role_action_def.role_id AND'
         ' record_def.id = role_action_def.def_id AND'
         ' action.id = role_action_def.action_id AND'
         ' role_action_def.account_id = '+account_id+' AND'
         ' record_def.account_id='+account_id+' AND'
         ' def_id='+def_id)

In a SQL statement like what you’re constructing, multiline strings would also be fine. But if the extra whitespace a multiline string would contain would be a problem, then this would be a good way to achieve what you want.


回答 2

打破行\对我的作品。这是一个例子:

longStr = "This is a very long string " \
        "that I wrote to help somebody " \
        "who had a question about " \
        "writing long strings in Python"

Breaking lines by \ works for me. Here is an example:

longStr = "This is a very long string " \
        "that I wrote to help somebody " \
        "who had a question about " \
        "writing long strings in Python"

回答 3

我发现自己对此很满意:

string = """This is a
very long string,
containing commas,
that I split up
for readability""".replace('\n',' ')

I found myself happy with this one:

string = """This is a
very long string,
containing commas,
that I split up
for readability""".replace('\n',' ')

回答 4

我发现在构建长字符串时,通常会执行诸如构建SQL查询之类的事情,在这种情况下,这是最好的:

query = ' '.join((  # note double parens, join() takes an iterable
    "SELECT foo",
    "FROM bar",
    "WHERE baz",
))

莱文的建议是好的,但可能容易出错:

query = (
    "SELECT foo"
    "FROM bar"
    "WHERE baz"
)

query == "SELECT fooFROM barWHERE baz"  # probably not what you want

I find that when building long strings, you are usually doing something like building an SQL query, in which case this is best:

query = ' '.join((  # note double parens, join() takes an iterable
    "SELECT foo",
    "FROM bar",
    "WHERE baz",
))

What Levon suggested is good, but might be vulnerable to mistakes:

query = (
    "SELECT foo"
    "FROM bar"
    "WHERE baz"
)

query == "SELECT fooFROM barWHERE baz"  # probably not what you want

回答 5

您还可以在使用“”符号时串联变量:

foo = '1234'

long_string = """fosdl a sdlfklaskdf as
as df ajsdfj asdfa sld
a sdf alsdfl alsdfl """ +  foo + """ aks
asdkfkasdk fak"""

编辑:找到了一种更好的方法,命名为params和.format():

body = """
<html>
<head>
</head>
<body>
    <p>Lorem ipsum.</p>
    <dl>
        <dt>Asdf:</dt>     <dd><a href="{link}">{name}</a></dd>
    </dl>
    </body>
</html>
""".format(
    link='http://www.asdf.com',
    name='Asdf',
)

print(body)

You can also concatenate variables in when using “”” notation:

foo = '1234'

long_string = """fosdl a sdlfklaskdf as
as df ajsdfj asdfa sld
a sdf alsdfl alsdfl """ +  foo + """ aks
asdkfkasdk fak"""

EDIT: Found a better way, with named params and .format():

body = """
<html>
<head>
</head>
<body>
    <p>Lorem ipsum.</p>
    <dl>
        <dt>Asdf:</dt>     <dd><a href="{link}">{name}</a></dd>
    </dl>
    </body>
</html>
""".format(
    link='http://www.asdf.com',
    name='Asdf',
)

print(body)

回答 6

此方法使用:

  • 只需一个反斜杠即可避免初始换行
  • 通过使用三引号引起来的字符串,几乎没有内部标点符号
  • 使用textwrap inspect模块去除局部缩进
  • account_iddef_id变量使用python 3.6格式的字符串插值(’f’)。

这种方式对我来说似乎是最pythonic的。

# import textwrap  # See update to answer below
import inspect

# query = textwrap.dedent(f'''\
query = inspect.cleandoc(f'''
    SELECT action.descr as "action", 
    role.id as role_id,
    role.descr as role
    FROM 
    public.role_action_def,
    public.role,
    public.record_def, 
    public.action
    WHERE role.id = role_action_def.role_id AND
    record_def.id = role_action_def.def_id AND
    action.id = role_action_def.action_id AND
    role_action_def.account_id = {account_id} AND
    record_def.account_id={account_id} AND
    def_id={def_id}'''
)

更新:1/29/2019合并@ShadowRanger的建议使用inspect.cleandoc代替textwrap.dedent

This approach uses:

  • just one backslash to avoid an initial linefeed
  • almost no internal punctuation by using a triple quoted string
  • strips away local indentation using the textwrap inspect module
  • uses python 3.6 formatted string interpolation (‘f’) for the account_id and def_id variables.

This way looks the most pythonic to me.

# import textwrap  # See update to answer below
import inspect

# query = textwrap.dedent(f'''\
query = inspect.cleandoc(f'''
    SELECT action.descr as "action", 
    role.id as role_id,
    role.descr as role
    FROM 
    public.role_action_def,
    public.role,
    public.record_def, 
    public.action
    WHERE role.id = role_action_def.role_id AND
    record_def.id = role_action_def.def_id AND
    action.id = role_action_def.action_id AND
    role_action_def.account_id = {account_id} AND
    record_def.account_id={account_id} AND
    def_id={def_id}'''
)

Update: 1/29/2019 Incorporate @ShadowRanger’s suggestion to use inspect.cleandoc instead of textwrap.dedent


回答 7

在Python> = 3.6中,您可以使用格式化字符串文字(f字符串)

query= f'''SELECT   action.descr as "action"
    role.id as role_id,
    role.descr as role
    FROM
    public.role_action_def,
    public.role,
    public.record_def,
    public.action
    WHERE role.id = role_action_def.role_id AND
    record_def.id = role_action_def.def_id AND
    action.id = role_action_def.action_id AND
    role_action_def.account_id = {account_id} AND
    record_def.account_id = {account_id} AND
    def_id = {def_id}'''

In Python >= 3.6 you can use Formatted string literals (f string)

query= f'''SELECT   action.descr as "action"
    role.id as role_id,
    role.descr as role
    FROM
    public.role_action_def,
    public.role,
    public.record_def,
    public.action
    WHERE role.id = role_action_def.role_id AND
    record_def.id = role_action_def.def_id AND
    action.id = role_action_def.action_id AND
    role_action_def.account_id = {account_id} AND
    record_def.account_id = {account_id} AND
    def_id = {def_id}'''

回答 8

例如:

sql = ("select field1, field2, field3, field4 "
       "from table "
       "where condition1={} "
       "and condition2={}").format(1, 2)

Output: 'select field1, field2, field3, field4 from table 
         where condition1=1 and condition2=2'

如果condition的值应该是字符串,则可以这样:

sql = ("select field1, field2, field3, field4 "
       "from table "
       "where condition1='{0}' "
       "and condition2='{1}'").format('2016-10-12', '2017-10-12')

Output: "select field1, field2, field3, field4 from table where
         condition1='2016-10-12' and condition2='2017-10-12'"

For example:

sql = ("select field1, field2, field3, field4 "
       "from table "
       "where condition1={} "
       "and condition2={}").format(1, 2)

Output: 'select field1, field2, field3, field4 from table 
         where condition1=1 and condition2=2'

if the value of condition should be a string, you can do like this:

sql = ("select field1, field2, field3, field4 "
       "from table "
       "where condition1='{0}' "
       "and condition2='{1}'").format('2016-10-12', '2017-10-12')

Output: "select field1, field2, field3, field4 from table where
         condition1='2016-10-12' and condition2='2017-10-12'"

回答 9

textwrap.dedent这里找到了长字符串的最佳选择:

def create_snippet():
    code_snippet = textwrap.dedent("""\
        int main(int argc, char* argv[]) {
            return 0;
        }
    """)
    do_something(code_snippet)

I find textwrap.dedent the best for long strings as described here:

def create_snippet():
    code_snippet = textwrap.dedent("""\
        int main(int argc, char* argv[]) {
            return 0;
        }
    """)
    do_something(code_snippet)

回答 10

其他人已经提到了括号方法,但是我想在括号中添加,允许内联注释。

对每个片段进行评论:

nursery_rhyme = (
    'Mary had a little lamb,'          # Comments are great!
    'its fleece was white as snow.'
    'And everywhere that Mary went,'
    'her sheep would surely go.'       # What a pesky sheep.
)

继续后不允许发表评论:

当使用反斜杠连续行(\)时,不允许注释。您会收到一个SyntaxError: unexpected character after line continuation character错误消息。

nursery_rhyme = 'Mary had a little lamb,' \  # These comments
    'its fleece was white as snow.'       \  # are invalid!
    'And everywhere that Mary went,'      \
    'her sheep would surely go.'
# => SyntaxError: unexpected character after line continuation character

对Regex字符串的更好注释:

根据https://docs.python.org/3/library/re.html#re.VERBOSE的示例,

a = re.compile(
    r'\d+'  # the integral part
    r'\.'   # the decimal point
    r'\d*'  # some fractional digits
)
# Using VERBOSE flag, IDE usually can't syntax highight the string comment.
a = re.compile(r"""\d +  # the integral part
                   \.    # the decimal point
                   \d *  # some fractional digits""", re.X)

Others have mentioned the parentheses method already, but I’d like to add that with parentheses, inline comments are allowed.

Comment on each fragment:

nursery_rhyme = (
    'Mary had a little lamb,'          # Comments are great!
    'its fleece was white as snow.'
    'And everywhere that Mary went,'
    'her sheep would surely go.'       # What a pesky sheep.
)

Comment not allowed after continuation:

When using backslash line continuations (\ ), comments are not allowed. You’ll receive a SyntaxError: unexpected character after line continuation character error.

nursery_rhyme = 'Mary had a little lamb,' \  # These comments
    'its fleece was white as snow.'       \  # are invalid!
    'And everywhere that Mary went,'      \
    'her sheep would surely go.'
# => SyntaxError: unexpected character after line continuation character

Better comments for Regex strings:

Based on the example from https://docs.python.org/3/library/re.html#re.VERBOSE,

a = re.compile(
    r'\d+'  # the integral part
    r'\.'   # the decimal point
    r'\d*'  # some fractional digits
)
# Using VERBOSE flag, IDE usually can't syntax highight the string comment.
a = re.compile(r"""\d +  # the integral part
                   \.    # the decimal point
                   \d *  # some fractional digits""", re.X)

回答 11

我个人发现以下是用Python编写原始SQL查询的最佳方式(简单,安全和Pythonic),尤其是在使用Python的sqlite3模块时

query = '''
    SELECT
        action.descr as action,
        role.id as role_id,
        role.descr as role
    FROM
        public.role_action_def,
        public.role,
        public.record_def,
        public.action
    WHERE
        role.id = role_action_def.role_id
        AND record_def.id = role_action_def.def_id
        AND action.id = role_action_def.action_id
        AND role_action_def.account_id = ?
        AND record_def.account_id = ?
        AND def_id = ?
'''
vars = (account_id, account_id, def_id)   # a tuple of query variables
cursor.execute(query, vars)   # using Python's sqlite3 module

优点

  • 简洁的代码(Pythonic!)
  • 防止SQL注入
  • 与Python 2和Python 3兼容(毕竟是Pythonic)
  • 无需字符串连接
  • 无需确保每行的最右字符是一个空格

缺点

  • 由于查询中的变量已被?占位符替换,因此?当查询中有很多变量时,要跟踪哪个变量将被哪个Python变量替换可能会有些困难。

I personally find the following to be the best (simple, safe and Pythonic) way to write raw SQL queries in Python, especially when using Python’s sqlite3 module:

query = '''
    SELECT
        action.descr as action,
        role.id as role_id,
        role.descr as role
    FROM
        public.role_action_def,
        public.role,
        public.record_def,
        public.action
    WHERE
        role.id = role_action_def.role_id
        AND record_def.id = role_action_def.def_id
        AND action.id = role_action_def.action_id
        AND role_action_def.account_id = ?
        AND record_def.account_id = ?
        AND def_id = ?
'''
vars = (account_id, account_id, def_id)   # a tuple of query variables
cursor.execute(query, vars)   # using Python's sqlite3 module

Pros

  • Neat and simple code (Pythonic!)
  • Safe from SQL injection
  • Compatible with both Python 2 and Python 3 (it’s Pythonic after all)
  • No string concatenation required
  • No need to ensure that the right-most character of each line is a space

Cons

  • Since variables in the query are replaced by the ? placeholder, it may become a little difficult to keep track of which ? is to be substituted by which Python variable when there are lots of them in the query.

回答 12

我通常使用这样的东西:

text = '''
    This string was typed to be a demo
    on how could we write a multi-line
    text in Python.
'''

如果要删除每行中令人讨厌的空格,可以执行以下操作:

text = '\n'.join(line.lstrip() for line in text.splitlines())

I usually use something like this:

text = '''
    This string was typed to be a demo
    on how could we write a multi-line
    text in Python.
'''

If you want to remove annoying blank spaces in each line, you could do as follows:

text = '\n'.join(line.lstrip() for line in text.splitlines())

回答 13

您的实际代码不起作用,在“行”末尾缺少空格(例如: role.descr as roleFROM...

多行字符串有三引号:

string = """line
  line2
  line3"""

它将包含换行符和多余的空格,但是对于SQL来说这不是问题。

Your actual code shouldn’t work, you are missing whitespaces at the end of “lines” (eg: role.descr as roleFROM...)

There is triplequotes for multiline string:

string = """line
  line2
  line3"""

It will contain the line breaks and extra spaces, but for SQL that’s not a problem.


回答 14

您还可以将sql语句放置在单独的文件中,action.sql然后使用以下命令将其加载到py文件中:

with open('action.sql') as f:
   query = f.read()

因此,sql语句将与python代码分开。如果sql语句中有需要从python填充的参数,则可以使用字符串格式(例如%s或{field})

You can also place the sql-statement in a seperate file action.sql and load it in the py file with

with open('action.sql') as f:
   query = f.read()

So the sql-statements will be separated from the python code. If there are parameters in the sql statement which needs to be filled from python, you can use string formating (like %s or {field})


回答 15

“Àla” Scala方式(但是我认为这是OQ要求的最Python方式):

description = """
            | The intention of this module is to provide a method to 
            | pass meta information in markdown_ header files for 
            | using it in jinja_ templates. 
            | 
            | Also, to provide a method to use markdown files as jinja 
            | templates. Maybe you prefer to see the code than 
            | to install it.""".replace('\n            | \n','\n').replace('            | ',' ')

如果您想要没有跳线的最终str,只需将其放在\n第二个替换的第一个参数的开头:

.replace('\n            | ',' ')`.

注意:“ …模板”之间的白线。和“还,…”在后面需要一个空格|

“À la” Scala way (but I think is the most pythonic way as OQ demands):

description = """
            | The intention of this module is to provide a method to 
            | pass meta information in markdown_ header files for 
            | using it in jinja_ templates. 
            | 
            | Also, to provide a method to use markdown files as jinja 
            | templates. Maybe you prefer to see the code than 
            | to install it.""".replace('\n            | \n','\n').replace('            | ',' ')

If you want final str without jump lines, just put \n at the start of the first argument of the second replace:

.replace('\n            | ',' ')`.

Note: the white line between “…templates.” and “Also, …” requires a whitespace after the |.


回答 16

tl; dr:使用"""\"""包装字符串,如

string = """\
This is a long string
spanning multiple lines.
"""

官方python文档中

字符串文字可以跨越多行。一种方法是使用三引号:“”“ …”“”或”’…”’。行尾会自动包含在字符串中,但是可以通过在行尾添加\来防止这种情况。下面的例子:

print("""\
Usage: thingy [OPTIONS]
     -h                        Display this usage message
     -H hostname               Hostname to connect to
""")

产生以下输出(请注意,不包括初始换行符):

Usage: thingy [OPTIONS]
     -h                        Display this usage message
     -H hostname               Hostname to connect to

tl;dr: Use """\ and """ to wrap the string, as in

string = """\
This is a long string
spanning multiple lines.
"""

From the official python documentation:

String literals can span multiple lines. One way is using triple-quotes: “””…””” or ”’…”’. End of lines are automatically included in the string, but it’s possible to prevent this by adding a \ at the end of the line. The following example:

print("""\
Usage: thingy [OPTIONS]
     -h                        Display this usage message
     -H hostname               Hostname to connect to
""")

produces the following output (note that the initial newline is not included):

Usage: thingy [OPTIONS]
     -h                        Display this usage message
     -H hostname               Hostname to connect to

回答 17

嘿,尝试这种希望能起作用的方法,就像这种格式,它将像您已成功查询此属性一样,返回一条连续的行。

"message": f'you have successfully inquired about '
           f'{enquiring_property.title} Property owned by '
           f'{enquiring_property.client}'

Hey try something like this hope it works, like in this format it will return you a continuous line like you have successfully enquired about this property`

"message": f'you have successfully inquired about '
           f'{enquiring_property.title} Property owned by '
           f'{enquiring_property.client}'

回答 18

我使用递归函数来构建复杂的SQL查询。此技术通常可用于构建大型字符串,同时保持代码的可读性。

# Utility function to recursively resolve SQL statements.
# CAUTION: Use this function carefully, Pass correct SQL parameters {},
# TODO: This should never happen but check for infinite loops
def resolveSQL(sql_seed, sqlparams):
    sql = sql_seed % (sqlparams)
    if sql == sql_seed:
        return ' '.join([x.strip() for x in sql.split()])
    else:
        return resolveSQL(sql, sqlparams)

PS:看一下很棒的python-sqlparse库,可以根据需要漂亮地打印SQL查询。 http://sqlparse.readthedocs.org/en/latest/api/#sqlparse.format

I use a recursive function to build complex SQL Queries. This technique can generally be used to build large strings while maintaining code readability.

# Utility function to recursively resolve SQL statements.
# CAUTION: Use this function carefully, Pass correct SQL parameters {},
# TODO: This should never happen but check for infinite loops
def resolveSQL(sql_seed, sqlparams):
    sql = sql_seed % (sqlparams)
    if sql == sql_seed:
        return ' '.join([x.strip() for x in sql.split()])
    else:
        return resolveSQL(sql, sqlparams)

P.S: Have a look at the awesome python-sqlparse library to pretty print SQL queries if needed. http://sqlparse.readthedocs.org/en/latest/api/#sqlparse.format


回答 19

当代码(例如变量)缩进并且输出字符串应该是一个衬线(没有换行符)时,我认为另一种方法更易读:

def some_method():

    long_string = """
a presumptuous long string 
which looks a bit nicer 
in a text editor when
written over multiple lines
""".strip('\n').replace('\n', ' ')

    return long_string 

Another option that I think is more readable when the code (e.g variable) is indented and the output string should be a one liner (no newlines):

def some_method():

    long_string = """
a presumptuous long string 
which looks a bit nicer 
in a text editor when
written over multiple lines
""".strip('\n').replace('\n', ' ')

    return long_string 

回答 20

使用三引号。人们经常在程序开始时使用它们来创建文档字符串,以解释其目的以及与该文档创建相关的其他信息。人们还在功能中使用这些来解释功能的目的和应用。例:

'''
Filename: practice.py
File creator: me
File purpose: explain triple quotes
'''


def example():
    """This prints a string that occupies multiple lines!!"""
    print("""
    This
    is 
    a multi-line
    string!
    """)

Use triple quotation marks. People often use these to create docstrings at the start of programs to explain their purpose and other information relevant to its creation. People also use these in functions to explain the purpose and application of functions. Example:

'''
Filename: practice.py
File creator: me
File purpose: explain triple quotes
'''


def example():
    """This prints a string that occupies multiple lines!!"""
    print("""
    This
    is 
    a multi-line
    string!
    """)

回答 21

我喜欢这种方法,因为它具有阅读的特权。如果我们的弦长,那就没办法了!根据您所处的缩进级别,仍然限制为每行80个字符。。。嗯…无需赘述。我认为python样式指南仍然很模糊。我采用@Eero Aaltonen方法是因为它具有阅读和常识的特权。我知道样式指南应该对我们有帮助,而不会使我们的生活变得一团糟。谢谢!

class ClassName():
    def method_name():
        if condition_0:
            if condition_1:
                if condition_2:
                    some_variable_0 =\
"""
some_js_func_call(
    undefined, 
    {
        'some_attr_0': 'value_0', 
        'some_attr_1': 'value_1', 
        'some_attr_2': '""" + some_variable_1 + """'
    }, 
    undefined, 
    undefined, 
    true
)
"""

I like this approach because it privileges reading. In cases where we have long strings there is no way! Depending on the level of indentation you are in and still limited to 80 characters per line… Well… No need to say anything else. In my view the python style guides are still very vague. I took the @Eero Aaltonen approach because it privileges reading and common sense. I understand that style guides should help us and not make our lives a mess. Thanks!

class ClassName():
    def method_name():
        if condition_0:
            if condition_1:
                if condition_2:
                    some_variable_0 =\
"""
some_js_func_call(
    undefined, 
    {
        'some_attr_0': 'value_0', 
        'some_attr_1': 'value_1', 
        'some_attr_2': '""" + some_variable_1 + """'
    }, 
    undefined, 
    undefined, 
    true
)
"""

回答 22

官方python文档中

字符串文字可以跨越多行。一种方法是使用三引号:“”“ …”“”或”’…”’。行尾会自动包含在字符串中,但是可以通过在行尾添加\来防止这种情况。下面的例子:

print("""\
Usage: thingy [OPTIONS]
     -h                        Display this usage message
     -H hostname               Hostname to connect to
""")

产生以下输出(请注意,不包括初始换行符):

From the official python documentation:

String literals can span multiple lines. One way is using triple-quotes: “””…””” or ”’…”’. End of lines are automatically included in the string, but it’s possible to prevent this by adding a \ at the end of the line. The following example:

print("""\
Usage: thingy [OPTIONS]
     -h                        Display this usage message
     -H hostname               Hostname to connect to
""")

produces the following output (note that the initial newline is not included):


回答 23

为了在字典中定义一个长字符串, 保留换行符,但省略空格,我最终在一个常量中定义字符串,如下所示:

LONG_STRING = \
"""
This is a long sting
that contains newlines.
The newlines are important.
"""

my_dict = {
   'foo': 'bar',
   'string': LONG_STRING
}

For defining a long string inside a dict, keeping the newlines but omitting the spaces, I ended up defining the string in a constant like this:

LONG_STRING = \
"""
This is a long sting
that contains newlines.
The newlines are important.
"""

my_dict = {
   'foo': 'bar',
   'string': LONG_STRING
}

回答 24

作为Python中长字符串的一种通用方法,您可以使用三引号splitjoin

_str = ' '.join('''Lorem ipsum dolor sit amet, consectetur adipiscing 
        elit, sed do eiusmod tempor incididunt ut labore et dolore 
        magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation 
        ullamco laboris nisi ut aliquip ex ea commodo.'''.split())

输出:

'Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo.'

关于OP的与SQL查询有关的问题,下面的答案无视此构建SQL查询方法的正确性,并且仅关注以可读性和美观性方式构建长字符串,而没有其他导入。它还忽略了这带来的计算负荷。

使用三重引号,我们构建了一个长且可读的字符串,然后使用split()将该字符串分解为一个列表,从而去除了空格,然后将其与重新连接在一起' '.join()。最后,我们使用以下format()命令插入变量:

account_id = 123
def_id = 321

_str = '''
    SELECT action.descr AS "action", role.id AS role_id, role.descr AS role 
    FROM public.role_action_def, public.role, public.record_def, public.action
    WHERE role.id = role_action_def.role_id 
    AND record_def.id = role_action_def.def_id 
    AND' action.id = role_action_def.action_id 
    AND role_action_def.account_id = {} 
    AND record_def.account_id = {} 
    AND def_id = {}
    '''

query = ' '.join(_str.split()).format(account_id, account_id, def_id)

生成:

SELECT action.descr AS "action", role.id AS role_id, role.descr AS role FROM public.role_action_def, public.role, public.record_def, public.action WHERE role.id = role_action_def.role_id AND record_def.id = role_action_def.def_id AND\' action.id = role_action_def.action_id AND role_action_def.account_id = 123 AND record_def.account_id=123 AND def_id=321

编辑:这种方法不符合PEP8,但我有时发现它很有用

As a general approach to long strings in Python you can use triple quotes, split and join:

_str = ' '.join('''Lorem ipsum dolor sit amet, consectetur adipiscing 
        elit, sed do eiusmod tempor incididunt ut labore et dolore 
        magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation 
        ullamco laboris nisi ut aliquip ex ea commodo.'''.split())

Output:

'Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo.'

With regard to OP’s question relating to a SQL query, the answer below disregards the correctness of this approach to building SQL queries and focuses only on building long strings in a readable and aesthetic way without additional imports. It also disregards the computational load this entails.

Using triple quotes we build a long and readable string which we then break up into a list using split() thereby stripping the whitespace and then join it back together with ' '.join(). Finally we insert the variables using the format() command:

account_id = 123
def_id = 321

_str = '''
    SELECT action.descr AS "action", role.id AS role_id, role.descr AS role 
    FROM public.role_action_def, public.role, public.record_def, public.action
    WHERE role.id = role_action_def.role_id 
    AND record_def.id = role_action_def.def_id 
    AND' action.id = role_action_def.action_id 
    AND role_action_def.account_id = {} 
    AND record_def.account_id = {} 
    AND def_id = {}
    '''

query = ' '.join(_str.split()).format(account_id, account_id, def_id)

Produces:

SELECT action.descr AS "action", role.id AS role_id, role.descr AS role FROM public.role_action_def, public.role, public.record_def, public.action WHERE role.id = role_action_def.role_id AND record_def.id = role_action_def.def_id AND\' action.id = role_action_def.action_id AND role_action_def.account_id = 123 AND record_def.account_id=123 AND def_id=321

Edit: This approach is not in line with PEP8 but I find it useful at times


回答 25

通常,我将listjoin用于多行注释/字符串。

lines = list()
lines.append('SELECT action.enter code here descr as "action", ')
lines.append('role.id as role_id,')
lines.append('role.descr as role')
lines.append('FROM ')
lines.append('public.role_action_def,')
lines.append('public.role,')
lines.append('public.record_def, ')
lines.append('public.action')
query = " ".join(lines)

您可以使用任何字符串来连接所有此列表元素,例如’ \n‘(换行符)或’ ,‘(逗号)或’ ‘(空格)

干杯..!!

Generally, I use list and join for multi-line comments/string.

lines = list()
lines.append('SELECT action.enter code here descr as "action", ')
lines.append('role.id as role_id,')
lines.append('role.descr as role')
lines.append('FROM ')
lines.append('public.role_action_def,')
lines.append('public.role,')
lines.append('public.record_def, ')
lines.append('public.action')
query = " ".join(lines)

you can use any string to join all this list element like ‘\n‘(newline) or ‘,‘(comma) or ‘‘(space)

Cheers..!!