Rust: Remover operador ternário

Criado em 29 jan. 2012  ·  29Comentários  ·  Fonte: rust-lang/rust

Um dos comentários que ficou na minha cabeça depois do anúncio 0.1 foi alguém perguntando por que temos um operador ternário, já que é funcionalmente o mesmo que nossas if expressões. Eu simpatizo com este sentimento

Ultimamente, tenho ficado desconfiado com a rápida adição de recursos à linguagem e acho que devemos ser mais cautelosos ao nos comprometermos com coisas de que realmente não precisamos. Um dos mandatos originais após o anúncio do Rust era focar na remoção de recursos (está no FAQ do idioma), e eu não acho que haja como argumentar que tivemos sucesso nisso.

Reconhecidamente, o operador ternário é um recurso de baixa manutenção, mas sua remoção também é de baixo impacto.

A-frontend E-easy

Comentários muito úteis

Concordou. Gostaria de ter feito do JS uma linguagem de expressão. A grande divisão declaração / expressão motiva?: Mas Rust está livre disso, e if-else é suficiente.

/ser

Todos 29 comentários

Eu concordo. Eu estava me perguntando por que tínhamos a operadora ternária também.

Concordou. Gostaria de ter feito do JS uma linguagem de expressão. A grande divisão declaração / expressão motiva?: Mas Rust está livre disso, e if-else é suficiente.

/ser

Como um usuário pesado do operador?: Em C / C ++, prefiro a sintaxe compacta. Também acho que formata melhor quando a expressão é muito longa para caber em uma única linha:

let x = some_very_long_condational
     ? if_true
     : if_false

let x = if some_very_long_condational 
     { if_true}
     else { if_false}

A sintaxe pode piorar, na minha opinião, se if_true e if_false não couberem em uma única linha. Por exemplo, onde as chaves devem ser colocadas.

Apenas meus dois centavos.

Eu gosto:

let x = if some_very_long_condational { 
                 if_true
           } else { 
                 if_false
           }

Ele adiciona algumas linhas extras (a "outra linha" e o colchete final), mas o mantém limpo e você pode adicionar tanto código quanto quiser em qualquer um deles.

Eu uso muito o operador ternário em C ++, mas acho que a sintaxe é ruim. Você precisa identificar o? e: no meio de um mar de outros tokens para ver que é até um condicional. Com a expressão - se você tiver o token inicial indicando ao leitor "aqui vem uma condicional".

Bem, ainda prefiro a sintaxe do operador ?: . Acho sua escolha de formatação muito prolixa, especialmente para os casos simples quando if_true e if_false são expressões únicas (ao contrário de várias instruções que terminam em uma expressão).

No entanto, não farei nenhuma objeção se o operador?: For removido.

Também estou usando ?: todos os lugares, mas ainda acho que removê-lo seria uma boa ideia - isso libera dois (!) Sigilos ASCII em nossa sintaxe de expressão. Pense em todas as outras coisas incrivelmente enigmáticas que poderíamos fazer com eles.

Um uso não criptografado seria permiti-los como parte do nome do predicado.
Por exemplo, "vazio? ()" Em vez de "is_empty ()".

@marijnh ++ :)

Pessoalmente, não dou a mínima. Igor defendeu ternário em https://mail.mozilla.org/pipermail/rust-dev/2010-November/000110.html

Isso foi feito no pull req # 1705.

    return parent.index_of(child_a) < offset_b ? -1 : 1

parece infinitamente melhor do que

    return if parent.index_of(child_a) < offset_b {
        -1 
    } else {
        1
    }

Se tivermos que ser pythony sobre isso,

return -1 if parent.index_of(child_a) < offset_b else 1

seria muito melhor.

Eu concordo, não entendo por que ele teve que ser removido ... Por favor, não force os usuários do Rust a escrever código desnecessariamente pesado / detalhado, quando tal prática comum (operador ternário) existe na maioria, senão em todas as linguagens.

De qualquer forma, está feito, mas eu só queria adicionar minha voz àqueles que apoiam um estilo de código mais limpo.

Eu também sinto falta dessa sintaxe

Eu acho que há três efeitos conspiradores em ação aqui, viz

1) "A grande divisão declaração / expressão" (@BrendanEich);
2) Coerção de não-Booleanos em contextos Booleanos;
3) Mesmo as linguagens 'dinâmicas' não costumam ter 'sintaxe dinâmica' (macros reais) e 'semântica dinâmica' ( from __future__ import division do Python) atualmente.

(1) significa que if ... then ... else ... é fundamentalmente diferente de ... ? ... : ... , o que é uma distinção inteiramente dispensável. Existem casos extremos como return , mas no geral a distinção não é necessária.

(2) significa que você pode, em muitos idiomas, usar expressões arbitrárias como testes; isso só parece conveniente contanto que você ainda esteja usando seu primeiro idioma e se torna irritante assim que você começa com o segundo. Como apontado acima nesta discussão do reddit , não está claro por que uma lista vazia deve denotar false ou true - basta escrever if ( d.length == 0 ) ... e você ganhou _tanta_ clareza!

(3) significa que você está preso a tudo o que o comitê de linguagem oferece, e seja o que for, a linguagem provavelmente ficará presa a ele até que alguém apareça, bifurque ou reescreva a base de código e dê a ela um novo nome. Pode ser diferente; pode haver idiomas que permitem, digamos, use 'ternary conditions'; use 'empty lists are false'; . Existem precedentes para isso. Claro, muitas coisas falam contra essa flexibilidade porque você sempre terá que manter em mente esses "marcadores de desvio" e lembrar de copiá-los ao copiar e colar o programa. OTOH, se meros usuários pudessem mudar a sintaxe e a semântica da linguagem facilmente e pré-empacotar tais práticas em módulos instaláveis, isso poderia ajudar muito na evolução da linguagem.

@kevina Às vezes, a verbosidade não é uma coisa ruim, mas eu concordo que os operadores ternários limpam o código muito bem.

@caitp : o que exatamente está errado?

return if parent.index_of(child_a) < offset_b { -1 } else { 1 }

ou uma das minhas "cláusulas de abraço" favoritas

return 
    if parent.index_of(child_a) < offset_b { -1 } 
    else                                   {  1 }

... ou use uma correspondência, especialmente se houver várias condições ...

return match parent.index_of(child_a) < offset_by {
  true  => -1,
  false => 1
}

... e, claro, se for provável que seja reutilizado: basta movê-lo para uma função ...

return parent.is_child_before(offset_b)

Olha só ... você tem opções ... porque _tudo_ é uma expressão.

Nunca quis salvar os _s seis caracteres_ necessários para escrever if {} else {} vez de
() ? : , mais o encadeamento de condicionais adicionais parece muito melhor com if-as-an-expression. (Operadores ternários aninhados tornam-se confusos muito rapidamente.)

Na minha opinião: ao usar if-as-an-expression não vejo necessidade de injetar tantos espaços em branco desnecessários. Também acho que ele lê mais naturalmente do que o operador ternário, e a verbosidade adicional ajuda a separar as duas cláusulas visualmente. Isso é apenas meu $0.02

Acho que você pode ter interpretado mal o que eu disse (e note que isso foi há algum tempo)

Estou apenas apontando que não vejo como o operador ternário parece "infinitamente melhor" de alguma forma.
Em minha opinião, as formas comuns são infinitamente mais bonitas do que as formas de casos especiais.

O comentário está dizendo que, às vezes, as expressões condicionais são muito úteis, ao contrário das instruções condicionais. Deixar cair o suspensório é apenas subjetivamente uma melhoria

return parent.index_of(child_a) < offset_b ? -1 : 1

vs

return if parent.index_of(child_a) < offset_b { -1 } else { 1 }

@caitp o segundo aqui é infinitamente pior do que o primeiro? Rust's if else ainda é uma expressão (não uma declaração).

Meus pensamentos são:

  • O segundo parece que seria mais legível para alguém sem uma história de outras línguas e
  • Provavelmente seria melhor manter a sintaxe ? na manga para açúcar futuro (talvez relacionado à Opção, etc)

@mitchmindtree totalmente.

Novamente, você está entendendo mal o que o comentário dizia.

return if parent.index_of(child_a) < offset_b { -1 } else { 1 } ainda está avaliando a condicional como uma expressão (e, portanto, pode ser um operando para return ).

As chaves são feias, mas o ponto principal é sobre expressões condicionais, não sobre chaves. É sobre ser capaz de escrever return foo.bar.baz(<conditional operand>) versus if (<conditional operand>) { return foo.bar.baz(1); } else { return foo.bar.baz(2); }

Acho que o que realmente precisamos entender é que esse problema já existe há mais de três anos. Considerando que as pessoas não sentiram tanta falta dos ternários em três anos, acho que é seguro dizer que eles permanecerão afastados.

@caitp hmm Ainda não tenho certeza se estou

Na ferrugem você ainda pode fazer

return foo.bar.baz(if cond { 42 } else { 0 })

? (Estou ciente de que você não estava falando sobre colchetes, desculpe a confusão: smile_cat:)

Na época, em ToT, não havia como fazer isso no Rust.

Não tenho uma opinião forte, mas só quero acrescentar que se ? e : podem ser usados ​​para outras coisas, por que não usar algo como ?? e ?: vez disso, por exemplo cond ?? 43 ?: 0 ?

Por que mudar a maneira como os desenvolvedores estão acostumados há dezenas de anos?

Le sam. 24 out. 2015 02:46, Kevin Atkinson [email protected] a
écrit:

Não tenho uma opinião forte, mas só quero acrescentar que é? e pode
melhor ser usado para outro agradecimento, por que não usar algo como ?? e ?:
em vez de. então talvez cond ?? 43?: 0.

-
Responda a este e-mail diretamente ou visualize-o no GitHub
https://github.com/rust-lang/rust/issues/1698#issuecomment -150728625.

@RenaudParis Desculpe, o que eu quis dizer foi: Não tenho uma opinião forte, mas só quero acrescentar que, se ? e : podem ser melhor usados ​​para outras coisas, por que não use algo como ?? e ?: vez disso, por exemplo cond ?? 43 ?: 0 ?

Uma das razões pelas quais o operador ternário foi removido foi que "?" poderia ser usado para outra coisa no futuro. Minha sugestão foi usar outra operadora. cond ?? 43 ?: 0 ainda é menor do que if cond {43} else {0} .

Eu acho que é correto ser removido, entretanto. Não seria tão ruim se braçadeiras não fossem necessárias para uma única expressão. (E sim, eu sei o quanto isso é difícil no analisador, mas vale a pena - a legibilidade é muito importante)

por exemplo

if i ==0 
     return i
else 
      1  

ou mesmo

if i == 0  return i
    else 1  

Este formato é melhor do que

 if i == 0   ? return i
      : 1  

ou

if i == 0   
      ? return i 
      : 1  

versos

if i ==0 {
      return i
}
else {
    1
}      

muito feio / difícil de ler para algo tão comum.

Fica pior, mas mais fácil de ler se você tiver uma política de desenvolvimento contra aparelhos egípcios.

if i ==0
{
     return i
}
else
{
     1
 }      
Esta página foi útil?
0 / 5 - 0 avaliações