从左到右在Python 3中对列表进行操作的应用 [英] Left to right application of operations on a list in Python 3

查看:63
本文介绍了从左到右在Python 3中对列表进行操作的应用的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

是否有任何方法可以实现Python列表中从左到右的非延迟调用操作?

例如斯卡拉(Scala):

  val a =((1至50).map(_ * 4).filter(_< = 170).filter(_.toString.length == 2).filter(_%20 == 0).zipWithIndex.map {case(x,n)=>s"结果[$ n] = $ x"}.mkString(" ..)))a:字符串= Result [0] = 20 .. Result [1] = 40 .. Result [2] = 60 .. Result [3] = 80 

虽然我意识到很多人不喜欢上面的语法,但是我喜欢从左到右移动并随便添加任意操作的功能.

当执行三个或更多操作时,IMO的Python for 理解是不容易阅读的.结果似乎是我们需要将所有内容分解为大块.

  [对于f中的a在g(b)中,对于b在h(c)中,对于..] 

是否有提到上述方法的机会?

注意:我尝试了一些库,包括 toolz.functoolz .Python 3惰性评估使这一点变得复杂:每个级别都返回一个 map 对象.此外,尚不清楚它可以对输入的 list 进行操作.

解决方案

@JohanL的回答很好地完成了工作,以了解标准python库中最接近的等效项是什么.

我最终在2019年11月改编了Matt Hagy的要点,该要点现在在 pypi

在对可用的第三方库进行了相当全面的审查之后,看来 Pipe https://github.com/JulienPalard/Pipe 最适合需要.

您可以创建自己的管道功能.我将其用于整理下面显示的一些文本.粗线是工作发生的地方.所有这些 @Pipe 东西,我只需要编写一次即可重复使用.

此处的任务是在第一个文本中关联缩写:

  rawLabels ="国家":国家名称农业:从事农业的百分比最小值:在采矿业中所占的百分比男子:制造业所占百分比附言:在供电行业中所占的百分比缺点:建筑业所占百分比SI:在服务行业中所占的百分比鳍:从事金融工作的百分比SPS:在社会和个人服务业中使用的百分比TC:用于运输和通信的百分比. 

在第二个文本中带有关联的标签:

  mylabs =乡村农业采矿制造电力建设服务金融社会运输"; 

这是功能操作的一次性编码(在后续管道中重复使用):

  @Pipedef split(iterable,delim =''):对于s中的iterable:yield s.split(delim)@管道def trim(可迭代):对于s中的iterable:yield s.strip()@管道def pzip(iterable,coll):对于zip(list(iterable),coll)中的s:yield s@管道def slice(可迭代,暗淡):如果len(dim)== 1:对于x中的iterable:产生x [dim [0]]Elif len(dim)== 2:对于x中的iterable:对于x [dim [0]]中的y:产生y [dim [1]]@管道def toMap(iterable):返回dict(list(iterable)) 

这是很大的 finale :全部集中在一个管道中:

  labels =(rawLabels.split('\ n')|修剪|分裂(':')|切片([0])|pzip(mylabs.split(''))|toMap) 

结果:

  print('labels =%s'%repr(labels))labels = {'PS':'Power','Min':'Mining','Country':'Country','SPS':'Social','TC':'Transport','SI':'Service',骗局":建筑",金融":金融",农业":农业",人":制造业"} 

Is there any possible way to achieve a non-lazy left to right invocation of operations on a list in Python?

E.g. Scala:

 val a = ((1 to 50)
  .map(_ * 4)
  .filter( _ <= 170)
  .filter(_.toString.length == 2)
  .filter (_ % 20 == 0)
  .zipWithIndex
  .map{ case(x,n) => s"Result[$n]=$x"}
  .mkString("  .. "))

  a: String = Result[0]=20  .. Result[1]=40  .. Result[2]=60  .. Result[3]=80

While I realize many folks will not prefer the above syntax, I like the ability to move left to right and add arbitrary operations as we go.

The Python for comprehension is IMO not easy to read when there are three or more operations. The result seems to be we're required to break everything up into chunks.

[f(a) for a in g(b) for b in h(c) for ..]

Is there any chance for the approach mentioned?

Note: I tried out a few libraries including toolz.functoolz. That one is complicated by Python 3 lazy evaluation: each level returns a map object. In addition, it is not apparent that it can operate on an input list.

解决方案

The answer from @JohanL does a nice job of seeing what the closest equivalent is in standard python libraries.

I ended up adapting a gist from Matt Hagy in November 2019 that is now in pypi

https://pypi.org/project/infixpy/

from infixpy import *
a = (Seq(range(1,51))
     .map(lambda x: x * 4)
     .filter(lambda x: x <= 170)
     .filter(lambda x: len(str(x)) == 2)
     .filter( lambda x: x % 20 ==0)
     .enumerate() 
     .map(lambda x: 'Result[%d]=%s' %(x[0],x[1]))
     .mkstring(' .. '))
print(a)

  # Result[0]=20  .. Result[1]=40  .. Result[2]=60  .. Result[3]=80

Other approaches described in other answers

Older approaches

I found a more appealing toolkit in Fall 2018

https://github.com/dwt/fluent

After a fairly thorough review of the available third party libraries it seems the Pipe https://github.com/JulienPalard/Pipe best suits the needs .

You can create your own pipeline functions. I put it to work for wrangling some text shown below. the bolded line is where the work happens. All those @Pipe stuff I only have to code once and then can re-use.

The task here is to associate the abbreviation in the first text:

rawLabels="""Country: Name of country
Agr: Percentage employed in agriculture
Min: Percentage employed in mining
Man: Percentage employed in manufacturing
PS: Percentage employed in power supply industries
Con: Percentage employed in construction
SI: Percentage employed in service industries
Fin: Percentage employed in finance
SPS: Percentage employed in social and personal services
TC: Percentage employed in transport and communications"""

With an associated tag in this second text:

mylabs = "Country Agriculture Mining Manufacturing Power Construction Service Finance Social Transport"

Here's the one-time coding for the functional operations (reuse in subsequent pipelines):

@Pipe
def split(iterable, delim= ' '):
    for s in iterable: yield s.split(delim)

@Pipe
def trim(iterable):
    for s in iterable: yield s.strip()

@Pipe
def pzip(iterable,coll):
    for s in zip(list(iterable),coll): yield s

@Pipe
def slice(iterable, dim):
  if len(dim)==1:
    for x in iterable:
      yield x[dim[0]]
  elif len(dim)==2:
    for x in iterable:
      for y in x[dim[0]]:
        yield y[dim[1]]
    
@Pipe
def toMap(iterable):
  return dict(list(iterable))

And here's the big finale : all in one pipeline:

labels = (rawLabels.split('\n') 
     | trim 
     | split(':')
     | slice([0])
     | pzip(mylabs.split(' '))
     | toMap )

And the result:

print('labels=%s' % repr(labels))

labels={'PS': 'Power', 'Min': 'Mining', 'Country': 'Country', 'SPS': 'Social', 'TC': 'Transport', 'SI': 'Service', 'Con': 'Construction', 'Fin': 'Finance', 'Agr': 'Agriculture', 'Man': 'Manufacturing'}

这篇关于从左到右在Python 3中对列表进行操作的应用的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆