]> crepu.dev Git - config.git/blob - djavu-asus/elpy/rpc-venv/lib/python3.11/site-packages/yapf/yapflib/logical_line.py
Configuracion en desarrollo PC pega
[config.git] / djavu-asus / elpy / rpc-venv / lib / python3.11 / site-packages / yapf / yapflib / logical_line.py
1 # Copyright 2015 Google Inc. All Rights Reserved.
2 #
3 # Licensed under the Apache License, Version 2.0 (the "License");
4 # you may not use this file except in compliance with the License.
5 # You may obtain a copy of the License at
6 #
7 # http://www.apache.org/licenses/LICENSE-2.0
8 #
9 # Unless required by applicable law or agreed to in writing, software
10 # distributed under the License is distributed on an "AS IS" BASIS,
11 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 # See the License for the specific language governing permissions and
13 # limitations under the License.
14 """LogicalLine primitive for formatting.
15
16 A logical line is the containing data structure produced by the parser. It
17 collects all nodes (stored in FormatToken objects) that could appear on a single
18 line if there were no line length restrictions. It's then used by the parser to
19 perform the wrapping required to comply with the style guide.
20 """
21
22 from yapf_third_party._ylib2to3.fixer_util import syms as python_symbols
23
24 from yapf.pytree import pytree_utils
25 from yapf.pytree import split_penalty
26 from yapf.yapflib import format_token
27 from yapf.yapflib import style
28 from yapf.yapflib import subtypes
29
30
31 class LogicalLine(object):
32 """Represents a single logical line in the output.
33
34 Attributes:
35 depth: indentation depth of this line. This is just a numeric value used to
36 distinguish lines that are more deeply nested than others. It is not the
37 actual amount of spaces, which is style-dependent.
38 """
39
40 def __init__(self, depth, tokens=None):
41 """Constructor.
42
43 Creates a new logical line with the given depth an initial list of tokens.
44 Constructs the doubly-linked lists for format tokens using their built-in
45 next_token and previous_token attributes.
46
47 Arguments:
48 depth: indentation depth of this line
49 tokens: initial list of tokens
50 """
51 self.depth = depth
52 self._tokens = tokens or []
53 self.disable = False
54
55 if self._tokens:
56 # Set up a doubly linked list.
57 for index, tok in enumerate(self._tokens[1:]):
58 # Note, 'index' is the index to the previous token.
59 tok.previous_token = self._tokens[index]
60 self._tokens[index].next_token = tok
61
62 def CalculateFormattingInformation(self):
63 """Calculate the split penalty and total length for the tokens."""
64 # Say that the first token in the line should have a space before it. This
65 # means only that if this logical line is joined with a predecessor line,
66 # then there will be a space between them.
67 self.first.spaces_required_before = 1
68 self.first.total_length = len(self.first.value)
69
70 prev_token = self.first
71 prev_length = self.first.total_length
72 for token in self._tokens[1:]:
73 if (token.spaces_required_before == 0 and
74 _SpaceRequiredBetween(prev_token, token, self.disable)):
75 token.spaces_required_before = 1
76
77 tok_len = len(token.value) if not token.is_pseudo else 0
78
79 spaces_required_before = token.spaces_required_before
80 if isinstance(spaces_required_before, list):
81 assert token.is_comment, token
82
83 # If here, we are looking at a comment token that appears on a line
84 # with other tokens (but because it is a comment, it is always the last
85 # token). Rather than specifying the actual number of spaces here,
86 # hard code a value of 0 and then set it later. This logic only works
87 # because this comment token is guaranteed to be the last token in the
88 # list.
89 spaces_required_before = 0
90
91 token.total_length = prev_length + tok_len + spaces_required_before
92
93 # The split penalty has to be computed before {must|can}_break_before,
94 # because these may use it for their decision.
95 token.split_penalty += _SplitPenalty(prev_token, token)
96 token.must_break_before = _MustBreakBefore(prev_token, token)
97 token.can_break_before = (
98 token.must_break_before or _CanBreakBefore(prev_token, token))
99
100 prev_length = token.total_length
101 prev_token = token
102
103 def Split(self):
104 """Split the line at semicolons."""
105 if not self.has_semicolon or self.disable:
106 return [self]
107
108 llines = []
109 lline = LogicalLine(self.depth)
110 for tok in self._tokens:
111 if tok.value == ';':
112 llines.append(lline)
113 lline = LogicalLine(self.depth)
114 else:
115 lline.AppendToken(tok)
116
117 if lline.tokens:
118 llines.append(lline)
119
120 for lline in llines:
121 lline.first.previous_token = None
122 lline.last.next_token = None
123
124 return llines
125
126 ############################################################################
127 # Token Access and Manipulation Methods #
128 ############################################################################
129
130 def AppendToken(self, token):
131 """Append a new FormatToken to the tokens contained in this line."""
132 if self._tokens:
133 token.previous_token = self.last
134 self.last.next_token = token
135 self._tokens.append(token)
136
137 @property
138 def first(self):
139 """Returns the first non-whitespace token."""
140 return self._tokens[0]
141
142 @property
143 def last(self):
144 """Returns the last non-whitespace token."""
145 return self._tokens[-1]
146
147 ############################################################################
148 # Token -> String Methods #
149 ############################################################################
150
151 def AsCode(self, indent_per_depth=2):
152 """Return a "code" representation of this line.
153
154 The code representation shows how the line would be printed out as code.
155
156 TODO(eliben): for now this is rudimentary for debugging - once we add
157 formatting capabilities, this method will have other uses (not all tokens
158 have spaces around them, for example).
159
160 Arguments:
161 indent_per_depth: how much spaces to indent per depth level.
162
163 Returns:
164 A string representing the line as code.
165 """
166 indent = ' ' * indent_per_depth * self.depth
167 tokens_str = ' '.join(tok.value for tok in self._tokens)
168 return indent + tokens_str
169
170 def __str__(self): # pragma: no cover
171 return self.AsCode()
172
173 def __repr__(self): # pragma: no cover
174 tokens_repr = ','.join(
175 '{0}({1!r})'.format(tok.name, tok.value) for tok in self._tokens)
176 return 'LogicalLine(depth={0}, tokens=[{1}])'.format(
177 self.depth, tokens_repr)
178
179 ############################################################################
180 # Properties #
181 ############################################################################
182
183 @property
184 def tokens(self):
185 """Access the tokens contained within this line.
186
187 The caller must not modify the tokens list returned by this method.
188
189 Returns:
190 List of tokens in this line.
191 """
192 return self._tokens
193
194 @property
195 def lineno(self):
196 """Return the line number of this logical line.
197
198 Returns:
199 The line number of the first token in this logical line.
200 """
201 return self.first.lineno
202
203 @property
204 def start(self):
205 """The start of the logical line.
206
207 Returns:
208 A tuple of the starting line number and column.
209 """
210 return (self.first.lineno, self.first.column)
211
212 @property
213 def end(self):
214 """The end of the logical line.
215
216 Returns:
217 A tuple of the ending line number and column.
218 """
219 return (self.last.lineno, self.last.column + len(self.last.value))
220
221 @property
222 def is_comment(self):
223 return self.first.is_comment
224
225 @property
226 def has_semicolon(self):
227 return any(tok.value == ';' for tok in self._tokens)
228
229
230 def _IsIdNumberStringToken(tok):
231 return tok.is_keyword or tok.is_name or tok.is_number or tok.is_string
232
233
234 def _IsUnaryOperator(tok):
235 return subtypes.UNARY_OPERATOR in tok.subtypes
236
237
238 def _HasPrecedence(tok):
239 """Whether a binary operation has precedence within its context."""
240 node = tok.node
241
242 # We let ancestor be the statement surrounding the operation that tok is the
243 # operator in.
244 ancestor = node.parent.parent
245
246 while ancestor is not None:
247 # Search through the ancestor nodes in the parse tree for operators with
248 # lower precedence.
249 predecessor_type = pytree_utils.NodeName(ancestor)
250 if predecessor_type in ['arith_expr', 'term']:
251 # An ancestor "arith_expr" or "term" means we have found an operator
252 # with lower precedence than our tok.
253 return True
254 if predecessor_type != 'atom':
255 # We understand the context to look for precedence within as an
256 # arbitrary nesting of "arith_expr", "term", and "atom" nodes. If we
257 # leave this context we have not found a lower precedence operator.
258 return False
259 # Under normal usage we expect a complete parse tree to be available and
260 # we will return before we get an AttributeError from the root.
261 ancestor = ancestor.parent
262
263
264 def _PriorityIndicatingNoSpace(tok):
265 """Whether to remove spaces around an operator due to precedence."""
266 if not tok.is_arithmetic_op or not tok.is_simple_expr:
267 # Limit space removal to highest priority arithmetic operators
268 return False
269 return _HasPrecedence(tok)
270
271
272 def _IsSubscriptColonAndValuePair(token1, token2):
273 return (token1.is_number or token1.is_name) and token2.is_subscript_colon
274
275
276 def _SpaceRequiredBetween(left, right, is_line_disabled):
277 """Return True if a space is required between the left and right token."""
278 lval = left.value
279 rval = right.value
280 if (left.is_pseudo and _IsIdNumberStringToken(right) and
281 left.previous_token and _IsIdNumberStringToken(left.previous_token)):
282 # Space between keyword... tokens and pseudo parens.
283 return True
284 if left.is_pseudo or right.is_pseudo:
285 # There should be a space after the ':' in a dictionary.
286 if left.OpensScope():
287 return True
288 # The closing pseudo-paren shouldn't affect spacing.
289 return False
290 if left.is_continuation or right.is_continuation:
291 # The continuation node's value has all of the spaces it needs.
292 return False
293 if right.name in pytree_utils.NONSEMANTIC_TOKENS:
294 # No space before a non-semantic token.
295 return False
296 if _IsIdNumberStringToken(left) and _IsIdNumberStringToken(right):
297 # Spaces between keyword, string, number, and identifier tokens.
298 return True
299 if lval == ',' and rval == ':':
300 # We do want a space between a comma and colon.
301 return True
302 if style.Get('SPACE_INSIDE_BRACKETS'):
303 # Supersede the "no space before a colon or comma" check.
304 if left.OpensScope() and rval == ':':
305 return True
306 if right.ClosesScope() and lval == ':':
307 return True
308 if (style.Get('SPACES_AROUND_SUBSCRIPT_COLON') and
309 (_IsSubscriptColonAndValuePair(left, right) or
310 _IsSubscriptColonAndValuePair(right, left))):
311 # Supersede the "never want a space before a colon or comma" check.
312 return True
313 if rval in ':,':
314 # Otherwise, we never want a space before a colon or comma.
315 return False
316 if lval == ',' and rval in ']})':
317 # Add a space between ending ',' and closing bracket if requested.
318 return style.Get('SPACE_BETWEEN_ENDING_COMMA_AND_CLOSING_BRACKET')
319 if lval == ',':
320 # We want a space after a comma.
321 return True
322 if lval == 'from' and rval == '.':
323 # Space before the '.' in an import statement.
324 return True
325 if lval == '.' and rval == 'import':
326 # Space after the '.' in an import statement.
327 return True
328 if (lval == '=' and rval in {'.', ',,,'} and
329 subtypes.DEFAULT_OR_NAMED_ASSIGN not in left.subtypes):
330 # Space between equal and '.' as in "X = ...".
331 return True
332 if lval == ':' and rval in {'.', '...'}:
333 # Space between : and ...
334 return True
335 if ((right.is_keyword or right.is_name) and
336 (left.is_keyword or left.is_name)):
337 # Don't merge two keywords/identifiers.
338 return True
339 if (subtypes.SUBSCRIPT_COLON in left.subtypes or
340 subtypes.SUBSCRIPT_COLON in right.subtypes):
341 # A subscript shouldn't have spaces separating its colons.
342 return False
343 if (subtypes.TYPED_NAME in left.subtypes or
344 subtypes.TYPED_NAME in right.subtypes):
345 # A typed argument should have a space after the colon.
346 return True
347 if left.is_string:
348 if (rval == '=' and
349 subtypes.DEFAULT_OR_NAMED_ASSIGN_ARG_LIST in right.subtypes):
350 # If there is a type hint, then we don't want to add a space between the
351 # equal sign and the hint.
352 return False
353 if rval not in '[)]}.' and not right.is_binary_op:
354 # A string followed by something other than a subscript, closing bracket,
355 # dot, or a binary op should have a space after it.
356 return True
357 if right.ClosesScope():
358 # A string followed by closing brackets should have a space after it
359 # depending on SPACE_INSIDE_BRACKETS. A string followed by opening
360 # brackets, however, should not.
361 return style.Get('SPACE_INSIDE_BRACKETS')
362 if subtypes.SUBSCRIPT_BRACKET in right.subtypes:
363 # It's legal to do this in Python: 'hello'[a]
364 return False
365 if left.is_binary_op and lval != '**' and _IsUnaryOperator(right):
366 # Space between the binary operator and the unary operator.
367 return True
368 if left.is_keyword and _IsUnaryOperator(right):
369 # Handle things like "not -3 < x".
370 return True
371 if _IsUnaryOperator(left) and _IsUnaryOperator(right):
372 # No space between two unary operators.
373 return False
374 if left.is_binary_op or right.is_binary_op:
375 if lval == '**' or rval == '**':
376 # Space around the "power" operator.
377 return style.Get('SPACES_AROUND_POWER_OPERATOR')
378 # Enforce spaces around binary operators except the blocked ones.
379 block_list = style.Get('NO_SPACES_AROUND_SELECTED_BINARY_OPERATORS')
380 if lval in block_list or rval in block_list:
381 return False
382 if style.Get('ARITHMETIC_PRECEDENCE_INDICATION'):
383 if _PriorityIndicatingNoSpace(left) or _PriorityIndicatingNoSpace(right):
384 return False
385 else:
386 return True
387 else:
388 return True
389 if (_IsUnaryOperator(left) and lval != 'not' and
390 (right.is_name or right.is_number or rval == '(')):
391 # The previous token was a unary op. No space is desired between it and
392 # the current token.
393 return False
394 if (subtypes.DEFAULT_OR_NAMED_ASSIGN in left.subtypes and
395 subtypes.TYPED_NAME not in right.subtypes):
396 # A named argument or default parameter shouldn't have spaces around it.
397 return style.Get('SPACES_AROUND_DEFAULT_OR_NAMED_ASSIGN')
398 if (subtypes.DEFAULT_OR_NAMED_ASSIGN in right.subtypes and
399 subtypes.TYPED_NAME not in left.subtypes):
400 # A named argument or default parameter shouldn't have spaces around it.
401 return style.Get('SPACES_AROUND_DEFAULT_OR_NAMED_ASSIGN')
402 if (subtypes.VARARGS_LIST in left.subtypes or
403 subtypes.VARARGS_LIST in right.subtypes):
404 return False
405 if (subtypes.VARARGS_STAR in left.subtypes or
406 subtypes.KWARGS_STAR_STAR in left.subtypes):
407 # Don't add a space after a vararg's star or a keyword's star-star.
408 return False
409 if lval == '@' and subtypes.DECORATOR in left.subtypes:
410 # Decorators shouldn't be separated from the 'at' sign.
411 return False
412 if left.is_keyword and rval == '.':
413 # Add space between keywords and dots.
414 return lval not in {'None', 'print'}
415 if lval == '.' and right.is_keyword:
416 # Add space between keywords and dots.
417 return rval not in {'None', 'print'}
418 if lval == '.' or rval == '.':
419 # Don't place spaces between dots.
420 return False
421 if ((lval == '(' and rval == ')') or (lval == '[' and rval == ']') or
422 (lval == '{' and rval == '}')):
423 # Empty objects shouldn't be separated by spaces.
424 return False
425 if not is_line_disabled and (left.OpensScope() or right.ClosesScope()):
426 if (style.GetOrDefault('SPACES_AROUND_DICT_DELIMITERS', False) and (
427 (lval == '{' and _IsDictListTupleDelimiterTok(left, is_opening=True)) or
428 (rval == '}' and
429 _IsDictListTupleDelimiterTok(right, is_opening=False)))):
430 return True
431 if (style.GetOrDefault('SPACES_AROUND_LIST_DELIMITERS', False) and (
432 (lval == '[' and _IsDictListTupleDelimiterTok(left, is_opening=True)) or
433 (rval == ']' and
434 _IsDictListTupleDelimiterTok(right, is_opening=False)))):
435 return True
436 if (style.GetOrDefault('SPACES_AROUND_TUPLE_DELIMITERS', False) and (
437 (lval == '(' and _IsDictListTupleDelimiterTok(left, is_opening=True)) or
438 (rval == ')' and
439 _IsDictListTupleDelimiterTok(right, is_opening=False)))):
440 return True
441 if left.OpensScope() and right.OpensScope():
442 # Nested objects' opening brackets shouldn't be separated, unless enabled
443 # by SPACE_INSIDE_BRACKETS.
444 return style.Get('SPACE_INSIDE_BRACKETS')
445 if left.ClosesScope() and right.ClosesScope():
446 # Nested objects' closing brackets shouldn't be separated, unless enabled
447 # by SPACE_INSIDE_BRACKETS.
448 return style.Get('SPACE_INSIDE_BRACKETS')
449 if left.ClosesScope() and rval in '([':
450 # A call, set, dictionary, or subscript that has a call or subscript after
451 # it shouldn't have a space between them.
452 return False
453 if left.OpensScope() and _IsIdNumberStringToken(right):
454 # Don't separate the opening bracket from the first item, unless enabled
455 # by SPACE_INSIDE_BRACKETS.
456 return style.Get('SPACE_INSIDE_BRACKETS')
457 if left.is_name and rval in '([':
458 # Don't separate a call or array access from the name.
459 return False
460 if right.ClosesScope():
461 # Don't separate the closing bracket from the last item, unless enabled
462 # by SPACE_INSIDE_BRACKETS.
463 # FIXME(morbo): This might be too permissive.
464 return style.Get('SPACE_INSIDE_BRACKETS')
465 if lval == 'print' and rval == '(':
466 # Special support for the 'print' function.
467 return False
468 if left.OpensScope() and _IsUnaryOperator(right):
469 # Don't separate a unary operator from the opening bracket, unless enabled
470 # by SPACE_INSIDE_BRACKETS.
471 return style.Get('SPACE_INSIDE_BRACKETS')
472 if (left.OpensScope() and (subtypes.VARARGS_STAR in right.subtypes or
473 subtypes.KWARGS_STAR_STAR in right.subtypes)):
474 # Don't separate a '*' or '**' from the opening bracket, unless enabled
475 # by SPACE_INSIDE_BRACKETS.
476 return style.Get('SPACE_INSIDE_BRACKETS')
477 if rval == ';':
478 # Avoid spaces before a semicolon. (Why is there a semicolon?!)
479 return False
480 if lval == '(' and rval == 'await':
481 # Special support for the 'await' keyword. Don't separate the 'await'
482 # keyword from an opening paren, unless enabled by SPACE_INSIDE_BRACKETS.
483 return style.Get('SPACE_INSIDE_BRACKETS')
484 return True
485
486
487 def _MustBreakBefore(prev_token, cur_token):
488 """Return True if a line break is required before the current token."""
489 if prev_token.is_comment or (prev_token.previous_token and
490 prev_token.is_pseudo and
491 prev_token.previous_token.is_comment):
492 # Must break if the previous token was a comment.
493 return True
494 if (cur_token.is_string and prev_token.is_string and
495 IsSurroundedByBrackets(cur_token)):
496 # We want consecutive strings to be on separate lines. This is a
497 # reasonable assumption, because otherwise they should have written them
498 # all on the same line, or with a '+'.
499 return True
500 return cur_token.must_break_before
501
502
503 def _CanBreakBefore(prev_token, cur_token):
504 """Return True if a line break may occur before the current token."""
505 pval = prev_token.value
506 cval = cur_token.value
507 if pval == 'yield' and cval == 'from':
508 # Don't break before a yield argument.
509 return False
510 if pval in {'async', 'await'} and cval in {'def', 'with', 'for'}:
511 # Don't break after sync keywords.
512 return False
513 if cur_token.split_penalty >= split_penalty.UNBREAKABLE:
514 return False
515 if pval == '@':
516 # Don't break right after the beginning of a decorator.
517 return False
518 if cval == ':':
519 # Don't break before the start of a block of code.
520 return False
521 if cval == ',':
522 # Don't break before a comma.
523 return False
524 if prev_token.is_name and cval == '(':
525 # Don't break in the middle of a function definition or call.
526 return False
527 if prev_token.is_name and cval == '[':
528 # Don't break in the middle of an array dereference.
529 return False
530 if cur_token.is_comment and prev_token.lineno == cur_token.lineno:
531 # Don't break a comment at the end of the line.
532 return False
533 if subtypes.UNARY_OPERATOR in prev_token.subtypes:
534 # Don't break after a unary token.
535 return False
536 if not style.Get('ALLOW_SPLIT_BEFORE_DEFAULT_OR_NAMED_ASSIGNS'):
537 if (subtypes.DEFAULT_OR_NAMED_ASSIGN in cur_token.subtypes or
538 subtypes.DEFAULT_OR_NAMED_ASSIGN in prev_token.subtypes):
539 return False
540 return True
541
542
543 def IsSurroundedByBrackets(tok):
544 """Return True if the token is surrounded by brackets."""
545 paren_count = 0
546 brace_count = 0
547 sq_bracket_count = 0
548 previous_token = tok.previous_token
549 while previous_token:
550 if previous_token.value == ')':
551 paren_count -= 1
552 elif previous_token.value == '}':
553 brace_count -= 1
554 elif previous_token.value == ']':
555 sq_bracket_count -= 1
556
557 if previous_token.value == '(':
558 if paren_count == 0:
559 return previous_token
560 paren_count += 1
561 elif previous_token.value == '{':
562 if brace_count == 0:
563 return previous_token
564 brace_count += 1
565 elif previous_token.value == '[':
566 if sq_bracket_count == 0:
567 return previous_token
568 sq_bracket_count += 1
569
570 previous_token = previous_token.previous_token
571 return None
572
573
574 def _IsDictListTupleDelimiterTok(tok, is_opening):
575 assert tok
576
577 if tok.matching_bracket is None:
578 return False
579
580 if is_opening:
581 open_tok = tok
582 close_tok = tok.matching_bracket
583 else:
584 open_tok = tok.matching_bracket
585 close_tok = tok
586
587 # There must be something in between the tokens
588 if open_tok.next_token == close_tok:
589 return False
590
591 assert open_tok.next_token.node
592 assert open_tok.next_token.node.parent
593
594 return open_tok.next_token.node.parent.type in [
595 python_symbols.dictsetmaker,
596 python_symbols.listmaker,
597 python_symbols.testlist_gexp,
598 ]
599
600
601 _LOGICAL_OPERATORS = frozenset({'and', 'or'})
602 _BITWISE_OPERATORS = frozenset({'&', '|', '^'})
603 _ARITHMETIC_OPERATORS = frozenset({'+', '-', '*', '/', '%', '//', '@'})
604
605
606 def _SplitPenalty(prev_token, cur_token):
607 """Return the penalty for breaking the line before the current token."""
608 pval = prev_token.value
609 cval = cur_token.value
610 if pval == 'not':
611 return split_penalty.UNBREAKABLE
612
613 if cur_token.node_split_penalty > 0:
614 return cur_token.node_split_penalty
615
616 if style.Get('SPLIT_BEFORE_LOGICAL_OPERATOR'):
617 # Prefer to split before 'and' and 'or'.
618 if pval in _LOGICAL_OPERATORS:
619 return style.Get('SPLIT_PENALTY_LOGICAL_OPERATOR')
620 if cval in _LOGICAL_OPERATORS:
621 return 0
622 else:
623 # Prefer to split after 'and' and 'or'.
624 if pval in _LOGICAL_OPERATORS:
625 return 0
626 if cval in _LOGICAL_OPERATORS:
627 return style.Get('SPLIT_PENALTY_LOGICAL_OPERATOR')
628
629 if style.Get('SPLIT_BEFORE_BITWISE_OPERATOR'):
630 # Prefer to split before '&', '|', and '^'.
631 if pval in _BITWISE_OPERATORS:
632 return style.Get('SPLIT_PENALTY_BITWISE_OPERATOR')
633 if cval in _BITWISE_OPERATORS:
634 return 0
635 else:
636 # Prefer to split after '&', '|', and '^'.
637 if pval in _BITWISE_OPERATORS:
638 return 0
639 if cval in _BITWISE_OPERATORS:
640 return style.Get('SPLIT_PENALTY_BITWISE_OPERATOR')
641
642 if (subtypes.COMP_FOR in cur_token.subtypes or
643 subtypes.COMP_IF in cur_token.subtypes):
644 # We don't mind breaking before the 'for' or 'if' of a list comprehension.
645 return 0
646 if subtypes.UNARY_OPERATOR in prev_token.subtypes:
647 # Try not to break after a unary operator.
648 return style.Get('SPLIT_PENALTY_AFTER_UNARY_OPERATOR')
649 if pval == ',':
650 # Breaking after a comma is fine, if need be.
651 return 0
652 if pval == '**' or cval == '**':
653 return split_penalty.STRONGLY_CONNECTED
654 if (subtypes.VARARGS_STAR in prev_token.subtypes or
655 subtypes.KWARGS_STAR_STAR in prev_token.subtypes):
656 # Don't split after a varargs * or kwargs **.
657 return split_penalty.UNBREAKABLE
658 if prev_token.OpensScope() and cval != '(':
659 # Slightly prefer
660 return style.Get('SPLIT_PENALTY_AFTER_OPENING_BRACKET')
661 if cval == ':':
662 # Don't split before a colon.
663 return split_penalty.UNBREAKABLE
664 if cval == '=':
665 # Don't split before an assignment.
666 return split_penalty.UNBREAKABLE
667 if (subtypes.DEFAULT_OR_NAMED_ASSIGN in prev_token.subtypes or
668 subtypes.DEFAULT_OR_NAMED_ASSIGN in cur_token.subtypes):
669 # Don't break before or after an default or named assignment.
670 return split_penalty.UNBREAKABLE
671 if cval == '==':
672 # We would rather not split before an equality operator.
673 return split_penalty.STRONGLY_CONNECTED
674 if cur_token.ClosesScope():
675 # Give a slight penalty for splitting before the closing scope.
676 return 100
677 return 0