É possível declarar apenas uma variável sem atribuir nenhum valor no Python?

288

É possível declarar uma variável em Python, assim?

var

para que seja inicializado como Nenhum? Parece que o Python permite isso, mas assim que você acessa, ele trava. Isso é possível? Se não, por que?

EDIT: Eu quero fazer isso para casos como este:

value

for index in sequence:

   if value == None and conditionMet:
       value = index
       break

Duplicado

Relacionado

Joan Venge
fonte
1
pode postar um pequeno programa que causa isso, por favor.
Preet Sangha
Você postou uma pergunta duplicada, votando para encerrá-la em favor da outra.
21789 Jerub
Ainda há alguma diferença, este lida com a impossibilidade de usar uma variável apenas declarando.
Joan Venge
Não existe realmente algo como declarar uma variável no mundo python, como explica sua primeira pergunta.
Harley Holcombe
1
por que alguém nunca disse 'apenas atribuir a ele' porque as variáveis ​​não existem antes de serem atribuídas ao período. E variáveis ​​em python não contêm as informações de tipo. Objetos fazem isso. As variáveis ​​são apenas para manter o objeto naquele momento. Além disso, o programa acima deve lançar uma exceção NameError na primeira linha. (Isso é o que eu recebo em 2.X e 3.X ambos)
osirisgothra

Respostas:

359

Por que não fazer isso:

var = None

Python é dinâmico, então você não precisa declarar coisas; eles existem automaticamente no primeiro escopo em que foram atribuídos. Portanto, tudo o que você precisa é de uma declaração de atribuição antiga regular, como acima.

Isso é legal, porque você nunca terminará com uma variável não inicializada. Mas tenha cuidado - isso não significa que você não acabará com variáveis ​​inicializadas incorretamente . Se você iniciar algo None, verifique se é isso que realmente deseja e atribua algo mais significativo, se puder.

Todd Gamblin
fonte
1
Eu ia fazer isso, mas apenas pensei implicitamente que faria isso.
19139 Joan Venge
7
O ponto é que isso seja explícito, não implícito. Não adivinhar qual é o valor inicial. Não é de admirar se uma variável não inicializada lança uma exceção ou magicamente tem um valor útil.
315/09 S.Lott
2
O único problema que tenho com isso é que eu estava monitorando um contador (minValue) e, sempre que um valor era menor que ele, eu o estava configurando para se tornar o novo minValue. Se eu declarasse minValue como None originalmente, aparentemente ainda será menor do que qualquer número com o qual eu o comparei. I terminou apenas inicializa-la sys.maxint
TJ Biddle
... eles existem automaticamente no primeiro escopo em que foram atribuídos. Então, você precisa caçar a primeira tarefa e descobrir. ugh!
Ed Randall
56

Eu recomendo que você leia Outras línguas têm "variáveis" (adicionei-o como um link relacionado) - em dois minutos você saberá que o Python tem "nomes", não "variáveis".

val = None
# ...
if val is None:
   val = any_object
jfs
fonte
Você também pode escrever val = val or any_objectpara inicializá-lo.
Zoltán
1
@ Zoltán: quebra se um valor válido para val for "false", por exemplo, zero ou vazio. Use ispara testar se um valor é None.
jfs
Depois de ler o artigo no link fornecido, parece ser pouco mais que sofisma semântico.
Andrew P.
29

No Python 3.6+, você pode usar as Anotações de variáveis ​​para isso:

https://www.python.org/dev/peps/pep-0526/#abstract

O PEP 484 introduziu dicas de tipo, também conhecidas como anotações de tipo. Embora seu foco principal fosse anotações de funções, também introduziu a noção de comentários de tipo para anotar variáveis:

# 'captain' is a string (Note: initial value is a problem)
captain = ...  # type: str

O PEP 526 visa adicionar sintaxe ao Python para anotar os tipos de variáveis ​​(incluindo variáveis ​​de classe e variáveis ​​de instância), em vez de expressá-las através de comentários:

captain: str  # Note: no initial value!

Parece estar mais diretamente alinhado com o que você estava perguntando "É possível declarar apenas uma variável sem atribuir qualquer valor no Python?"

Tagar
fonte
2
Resposta excelente
Ben
16

Não tenho certeza do que você está tentando fazer. Python é uma linguagem muito dinâmica; você normalmente não precisa declarar variáveis ​​até que você realmente as atribua ou use. Eu acho que o que você quer fazer é apenas

foo = None

que irá atribuir o valor Noneà variável foo.

Edição: O que você realmente parece querer fazer é apenas isso:

#note how I don't do *anything* with value here
#we can just start using it right inside the loop

for index in sequence:
   if conditionMet:
       value = index
       break

try:
    doSomething(value)
except NameError:
    print "Didn't find anything"

É um pouco difícil dizer se esse é realmente o estilo certo para usar em um exemplo de código tão curto, mas é uma maneira mais "pitônica" de trabalhar.

EDIT: abaixo é comentado por JFS (postado aqui para mostrar o código)

Não relacionado à pergunta do OP, mas o código acima pode ser reescrito como:

for item in sequence:
    if some_condition(item): 
       found = True
       break
else: # no break or len(sequence) == 0
    found = False

if found:
   do_something(item)

OBSERVAÇÃO: se some_condition()gera uma exceção, ele foundé ilimitado.
OBSERVAÇÃO: se len (sequência) == 0, então itemnão será vinculado.

O código acima não é aconselhável. Seu objetivo é ilustrar como as variáveis ​​locais funcionam, ou seja, se "variável" é "definida" pode ser determinada apenas em tempo de execução nesse caso. Maneira preferível:

for item in sequence:
    if some_condition(item):
       do_something(item)
       break

Ou

found = False
for item in sequence:
    if some_condition(item):
       found = True
       break

if found:
   do_something(item)
kquinn
fonte
Existe uma diferença entre uma linguagem dinâmica e uma linguagem muito dinâmica?
Gavin Miller
Há um ótimo artigo explicando os diferentes eixos da digitação da linguagem de programação e como eles são contínuos, e não valores booleanos; infelizmente eu nunca pode achar que artigo novamente quando eu quero citá-la :( Eu considero Python "muito dinâmico", porque é na extremidade de vários eixos.
kquinn
3

Normalmente, inicializo a variável para algo que denota o tipo

var = ""

ou

var = 0

Se for um objeto, não o inicialize até que você o instancie:

var = Var()
Andrew Hare
fonte
3

Bem, se você deseja verificar se uma variável está definida ou não, por que não verificar se está nas matrizes locals () ou globals ()? Seu código reescrito:

for index in sequence:
   if 'value' not in globals() and conditionMet:
       value = index
       break

Se você procura uma variável local, substitua globals () por locals ().

Johan
fonte
2

Primeiro de tudo, minha resposta à pergunta que você fez originalmente

P: Como descubro se uma variável está definida em um ponto do meu código?

R: Leia o arquivo de origem até ver uma linha em que essa variável está definida.

Além disso, você deu um exemplo de código de que existem várias permutações bastante pitônicas. Você está procurando uma maneira de varrer uma sequência em busca de elementos que correspondam a uma condição, então, aqui estão algumas soluções:

def findFirstMatch(sequence):
    for value in sequence:
        if matchCondition(value):
            return value

    raise LookupError("Could not find match in sequence")

Claramente, neste exemplo, você pode substituir o raise por um return Nonedependendo do que deseja alcançar.

Se você quisesse tudo que correspondesse à condição, poderia fazer o seguinte:

def findAllMatches(sequence):
    matches = []
    for value in sequence:
        if matchCondition(value):
            matches.append(value)

    return matches

Existe outra maneira de fazer isso com yield que eu não vou me incomodar em mostrar a você, porque é bastante complicado na maneira como funciona.

Além disso, existe uma maneira única de conseguir isso:

all_matches = [value for value in sequence if matchCondition(value)]
Jerub
fonte
2

Se estou entendendo o seu exemplo corretamente, você não precisa se referir a 'value' na instrução if de qualquer maneira. Você está saindo do circuito assim que possível.

value = None
for index in sequence:
   doSomethingHere
   if conditionMet:
       value = index
       break 
fholo
fonte
1

Parece que você está tentando escrever C em Python. Se você deseja encontrar algo em uma sequência, o Python possui funções internas para fazer isso, como

value = sequence.index(blarg)

fonte
1

É uma boa pergunta e, infelizmente, respostas ruins, como var = Nonejá está atribuindo um valor, e se o seu script for executado várias vezes, ele será substituído porNone sempre.

Não é o mesmo que definir sem atribuição. Ainda estou tentando descobrir como ignorar esse problema.

zinturis
fonte
1

É possível declarar uma variável em Python (var = None):

def decl_var(var=None):
if var is None:
    var = []
var.append(1)
return var
Abderrahim
fonte
0
var_str = str()
var_int = int()
Zaur
fonte
impertinente impertinente homem impertinente! variáveis ​​não associam tipo, objetos fazem. var_str não deve ser restringido em um nome tão genérico. Se você fizer isso, faça com que seja significativo como 'var_age' ou 'var_name', por exemplo. Esses valores podem ser tomados como números inteiros ou seqüências de caracteres ou o que você quiser, e alterados para objetos, o próprio espírito do que torna o python diferente de outras linguagens. Eles dizem que se você precisar fazer isso o tempo todo, provavelmente deseja usar outro idioma.
Osirisgothra 9/07
0

Se Nonefor um valor de dados válido, você precisará da variável de outra maneira. Você poderia usar:

var = object()

Este sentinela é sugerido por Nick Coghlan .

Chris_Rands
fonte
0

Você pode enganar um intérprete com este oneliner feio. if None: var = None Ele não faz mais nada além de adicionar uma variável varao dicionário de variáveis ​​local, sem inicializá-lo. O intérprete lançará a exceção UnboundLocalError se você tentar usar essa variável em uma função posteriormente. Isso funcionaria para versões python muito antigas também. Não é simples, nem bonito, mas não espere muito do python.

ZAB
fonte