当我们偶然发现下面的行为时,我和一些朋友正在讨论与Python内存管理相关的事情:
In [46]: l = ({} for _ in range(6))
In [47]: [ id(i) for i in l]
Out[47]:
[4371243648, # A
4371245048, # B
4371243648, # A
4371245048, # B
4371243648, # etc.
4371245048]
Run Code Online (Sandbox Code Playgroud)
令人惊讶的是,我们似乎没有明确定义的行为:每次dict既不是新的也不是每次都是相同的引用.
最重要的是,我们得到了这种奇怪的行为(代码不是在这两个片段之间的解释器中运行).
In [48]: m = ({} for _ in range(6))
In [49]: [ id(i) for i in m]
Out[49]:
[4371154376, # C
4371245048, # B (same B as above!)
4371154376, # C
4371245048, # B
4371154376,
4371245048]
Run Code Online (Sandbox Code Playgroud)
谁能解释这种行为?使用list comprehensions(l = [{} for _ …
我正在使用Python来解析一个大文件.我想做的是
If condition =True
append to list A
else
append to list B
Run Code Online (Sandbox Code Playgroud)
我想为此使用生成器表达式 - 以节省内存.我正在加入实际的代码.
def is_low_qual(read):
lowqual_bp=(bq for bq in phred_quals(read) if bq < qual_threshold)
if iter_length(lowqual_bp) > num_allowed:
return True
else:
return False
lowqual=(read for read in SeqIO.parse(r_file,"fastq") if is_low_qual(read)==True)
highqual=(read for read in SeqIO.parse(r_file,"fastq") if is_low_qual(read)==False)
SeqIO.write(highqual,flt_out_handle,"fastq")
SeqIO.write(lowqual,junk_out_handle,"fastq")
def iter_length(the_gen):
return sum(1 for i in the_gen)
Run Code Online (Sandbox Code Playgroud) 我怎样才能获得一个可调用的工厂用于defaultdict以允许用理解填充它?我认为这可能不可能,但我想不出一个很好的理由呢?
>>> def foo(*args):
... # TODO
...
>>> from collections import defaultdict
>>> thing = foo(defaultdict, int)
>>> d = thing((i, i*i) for i in range(3))
>>> d[2]
# should return 4
>>> d[-1]
# should return 0
Run Code Online (Sandbox Code Playgroud) 我有以下代码:
import itertools
for c in ((yield from bin(n)[2:]) for n in range(10)):
print(c)
Run Code Online (Sandbox Code Playgroud)
输出是:
0
None
1
None
1
0
None
1
1
None
Run Code Online (Sandbox Code Playgroud)
......等等为什么会None
出现?如果我改为:
def hmm():
for n in range(10):
yield from bin(n)[2:]
for c in hmm():
print(c)
Run Code Online (Sandbox Code Playgroud)
然后我得到了我期望的东西:
0
1
1
0
1
1
Run Code Online (Sandbox Code Playgroud)
...等等.还有一种方法可以将它写为生成器表达式以获得与后者相同的结果吗?
我写的时候:
lines = (line.strip() for line in open('a_file'))
Run Code Online (Sandbox Code Playgroud)
文件是立即打开还是仅在我开始使用生成器表达式时才访问文件系统?
一方面我们有
[x for x in range(10)]
{x for x in range(10)}
{x: x for x in range(10)}
另一方面我们有
(x for x in range(10))
为什么前三个表达式称为“理解”,而最后一个称为“表达式”?它们几乎以相同的方式表示,我猜它们也以非常相似的方式工作。这背后有什么微妙的原因吗?这只是为了好奇。
参考:
python terminology list-comprehension generator-expression dictionary-comprehension
我想知道是否有一个简单的Pythonic方式(可能使用生成器)在列表中的每个项目上运行一个函数,并产生一个返回列表?
例:
def square_it(x):
return x*x
x_set = [0,1,2,3,4]
squared_set = square_it(x for x in x_set)
Run Code Online (Sandbox Code Playgroud)
我注意到,当我对此进行逐行调试时,传递给函数的对象是生成器.
因此,我收到一个错误:
TypeError: unsupported operand type(s) for *: 'generator' and 'generator'
我知道这个生成器表达式创建了一个传递给函数的生成器,但我想知道是否有一种很酷的方法来完成多次运行该函数只能通过指定一个iterable作为参数?(不修改函数以期望迭代).
在我看来,这种能力对于减少代码行非常有用,因为你不需要创建一个循环来使函数变得有趣,而一个变量将输出保存在列表中.
谢谢!
我有一个迭代delta
生成两个数字的元组(dx, dy)
,我想计算每个数的总和.以下不起作用,因为delta
在第一次迭代后处理.
x = sum(dx for dx, dy in delta)
y = sum(dy for dx, dy in delta)
Run Code Online (Sandbox Code Playgroud)
任何的想法?我想在莫名其妙地转动方向delta
为两个iterables dx
和dy
,但到目前为止已经达到什么.
生成器表达式是一个非常有用的工具,与列表推导相比具有巨大的优势,即它不为新数组分配内存.
我面对生成器表达式的问题,最终使我最终编写列表推导,是我只能使用这样一个生成器:
>>> names = ['John', 'George', 'Paul', 'Ringo']
>>> has_o = (name for name in names if 'o' in name)
>>> for name in has_o:
... print(name.upper())
...
JOHN
GEORGE
RINGO
>>> for name in has_o:
... print(name.lower())
...
>>>
Run Code Online (Sandbox Code Playgroud)
上面的代码说明了生成器表达式如何只能使用一次.这当然是因为生成器表达式返回生成器的实例,而不是定义可以反复实例化的生成器函数.
有没有办法在每次使用时克隆生成器,以使其可重用,或使生成器表达式语法返回生成器函数而不是单个实例?
有一个Django视图,Member
使用某个过滤器从数据库加载对象.
现在我需要改变这个逻辑以呈现一个特定的Member
第一个,并让其余的按照它们的自然顺序.
最直接的方法是立即执行查询,获取列表,删除并在开头插入项目.但是,如果仍然有任何方法可以利用QuerySet
懒惰的本性,我最好奇.
在C#中,我会写:
IEnumerable<Member> members = db.Members; // db.Members is lazy
members = Enumerable.Union( // construct a lazy sequence that traverses its arguments
new [] { specificMember },
members.Where(m => m != specificMember)
);
Run Code Online (Sandbox Code Playgroud)
当循环通过时members
,它将首先获得specificMember
然后使用任何延迟加载逻辑原始db.Members
使用.
有没有办法在Django和Python中做同样的事情?
python django generator-expression django-queryset lazy-sequences
python ×10
generator ×4
python-3.x ×2
defaultdict ×1
dictionary ×1
django ×1
iterable ×1
iterator ×1
terminology ×1
yield ×1