使用“in” 匹配数组中Python对象的属性

发布于 2024-07-03 23:59:55 字数 155 浏览 8 评论 0原文

我不记得我是否在做梦,但我似乎记得有一个功能允许类似的功能,

foo in iter_attr(array of python objects, attribute name)

我已经查看了文档,但这种事情不属于任何明显列出的标题

I don't remember whether I was dreaming or not but I seem to recall there being a function which allowed something like,

foo in iter_attr(array of python objects, attribute name)

I've looked over the docs but this kind of thing doesn't fall under any obvious listed headers

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(8

手心的海 2024-07-11 00:00:13

我想:

#!/bin/python
bar in dict(Foo)

就是你所想的。 当尝试查看 python 中的字典(python 版本的哈希表)中是否存在某个键时,有两种方法可以检查。 第一个是附加到字典的 has_key() 方法,第二个是上面给出的示例。 它将返回一个布尔值。

这应该可以回答你的问题。

现在有点偏离主题,将其与之前给出的列表理解答案联系起来(为了更清楚一点)。 列表推导式使用修饰符从基本的for循环构造一个列表。 举个例子(稍微澄清一下),在列表理解中使用 in dict 语言构造的方法:

假设你有一个二维字典 foo 并且您只需要包含键 bar 的第二维字典。 一种相对简单的方法是使用带有条件的列表理解,如下所示:

#!/bin/python
baz = dict([(key, value) for key, value in foo if bar in value])

注意末尾的if bar in value语句的**,这是一个修改子句,它告诉列表理解仅保留那些满足条件的键值对。**在本例中baz是一个新字典,仅包含 foo 中包含 bar 的字典(希望我没有错过该代码示例中的任何内容...您可能需要查看 < 中找到的列表理解文档a href="http://docs.python.org/tut/node7.html#SECTION007140000000000000000" rel="nofollow noreferrer">docs.python.org 教程 和 secnetix.de,如果您将来有疑问,这两个网站都是很好的参考。)。

I think:

#!/bin/python
bar in dict(Foo)

Is what you are thinking of. When trying to see if a certain key exists within a dictionary in python (python's version of a hash table) there are two ways to check. First is the has_key() method attached to the dictionary and second is the example given above. It will return a boolean value.

That should answer your question.

And now a little off topic to tie this in to the list comprehension answer previously given (for a bit more clarity). List Comprehensions construct a list from a basic for loop with modifiers. As an example (to clarify slightly), a way to use the in dict language construct in a list comprehension:

Say you have a two dimensional dictionary foo and you only want the second dimension dictionaries which contain the key bar. A relatively straightforward way to do so would be to use a list comprehension with a conditional as follows:

#!/bin/python
baz = dict([(key, value) for key, value in foo if bar in value])

Note the if bar in value at the end of the statement**, this is a modifying clause which tells the list comprehension to only keep those key-value pairs which meet the conditional.** In this case baz is a new dictionary which contains only the dictionaries from foo which contain bar (Hopefully I didn't miss anything in that code example... you may have to take a look at the list comprehension documentation found in docs.python.org tutorials and at secnetix.de, both sites are good references if you have questions in the future.).

梦在深巷 2024-07-11 00:00:12

如果您打算搜索任何相当大的东西,最好的选择是使用字典或集合。 否则,您基本上必须遍历迭代器的每个元素,直到找到您想要的元素。

如果这不一定是性能敏感的代码,那么列表理解方式应该可以工作。 但请注意,它的效率相当低,因为它会遍历迭代器的每个元素,然后再次返回,直到找到它想要的内容。

请记住,Python 拥有最有效的哈希算法之一。 利用它来发挥你的优势。

If you plan on searching anything of remotely decent size, your best bet is going to be to use a dictionary or a set. Otherwise, you basically have to iterate through every element of the iterator until you get to the one you want.

If this isn't necessarily performance sensitive code, then the list comprehension way should work. But note that it is fairly inefficient because it goes over every element of the iterator and then goes BACK over it again until it finds what it wants.

Remember, python has one of the most efficient hashing algorithms around. Use it to your advantage.

So要识趣 2024-07-11 00:00:11

我的想法可以使用列表理解来实现,但我认为有一个函数可以以稍微更简洁的方式完成此操作。

即 'bar' 是一个对象列表,所有对象都具有属性 'id'

神秘的功能方式:

foo = 12
foo in iter_attr(bar, 'id')

列表理解方式:

foo = 12
foo in [obj.id for obj in bar]

回想起来,列表理解方式无论如何都非常简洁。

What I was thinking of can be achieved using list comprehensions, but I thought that there was a function that did this in a slightly neater way.

i.e. 'bar' is a list of objects, all of which have the attribute 'id'

The mythical functional way:

foo = 12
foo in iter_attr(bar, 'id')

The list comprehension way:

foo = 12
foo in [obj.id for obj in bar]

In retrospect the list comprehension way is pretty neat anyway.

揽月 2024-07-11 00:00:10

您正在考虑的函数可能是operator.attrgettter。 例如,要获取包含每个对象的“id”属性值的列表:

import operator
ids = map(operator.attrgetter("id"), bar)

如果要检查该列表是否包含 id == 12 的对象,那么一个简洁且高效的方法(即不迭代整个列表)不必要地列出)方法是:

any(obj.id == 12 for obj in bar)

如果您想将 'in' 与 attrgetter 一起使用,同时仍然保留列表的惰性迭代:

import operator,itertools
foo = 12
foo in itertools.imap(operator.attrgetter("id"), bar)

The function you are thinking of is probably operator.attrgettter. For example, to get a list that contains the value of each object's "id" attribute:

import operator
ids = map(operator.attrgetter("id"), bar)

If you want to check whether the list contains an object with an id == 12, then a neat and efficient (i.e. doesn't iterate the whole list unnecessarily) way to do it is:

any(obj.id == 12 for obj in bar)

If you want to use 'in' with attrgetter, while still retaining lazy iteration of the list:

import operator,itertools
foo = 12
foo in itertools.imap(operator.attrgetter("id"), bar)

七禾 2024-07-11 00:00:08

不,你不是在做梦。 Python 有一个非常优秀的列表理解系统,可以让您非常优雅地操作列表,并且根据您想要完成的具体任务,可以通过几种方式来完成。 本质上,您所做的就是说“For item in list if criteria.matches”,然后您可以迭代结果或将结果转储到新列表中。

我将在这里抄袭深入了解 Python 中的一个示例,因为它非常优雅,而且它们'他们比我聪明。 在这里,他们获取目录中的文件列表,然后过滤该列表以查找与正则表达式条件匹配的所有文件。

 文件 = os.listdir(路径)                                
      测试 = re.compile("test\.py$", re.IGNORECASE)           
      files = [f for f in files if test.search(f)] 
  

对于您的示例,您可以在不使用正则表达式的情况下执行此操作,对于最后的表达式返回 true 匹配的任何内容。 还有其他选项,例如使用 filter() 函数,但如果我要选择,我会选择这个。

埃里克·西普尔

No, you were not dreaming. Python has a pretty excellent list comprehension system that lets you manipulate lists pretty elegantly, and depending on exactly what you want to accomplish, this can be done a couple of ways. In essence, what you're doing is saying "For item in list if criteria.matches", and from that you can just iterate through the results or dump the results into a new list.

I'm going to crib an example from Dive Into Python here, because it's pretty elegant and they're smarter than I am. Here they're getting a list of files in a directory, then filtering the list for all files that match a regular expression criteria.

    files = os.listdir(path)                               
    test = re.compile("test\.py$", re.IGNORECASE)          
    files = [f for f in files if test.search(f)]

You could do this without regular expressions, for your example, for anything where your expression at the end returns true for a match. There are other options like using the filter() function, but if I were going to choose, I'd go with this.

Eric Sipple

丑丑阿 2024-07-11 00:00:07

你总是可以自己写一个:

def iterattr(iterator, attributename):
    for obj in iterator:
        yield getattr(obj, attributename)

可以处理任何迭代的东西,无论是元组、列表还是其他什么。

我喜欢Python,它使这样的东西变得非常简单,没有必要的麻烦,而且在使用中这样的东西非常优雅。

you could always write one yourself:

def iterattr(iterator, attributename):
    for obj in iterator:
        yield getattr(obj, attributename)

will work with anything that iterates, be it a tuple, list, or whatever.

I love python, it makes stuff like this very simple and no more of a hassle than neccessary, and in use stuff like this is hugely elegant.

葬シ愛 2024-07-11 00:00:05

您是否想要获取具有特定属性的对象列表? 如果是这样,列表理解是执行此操作的正确方法。

result = [obj for obj in listOfObjs if hasattr(obj, 'attributeName')]

Are you looking to get a list of objects that have a certain attribute? If so, a list comprehension is the right way to do this.

result = [obj for obj in listOfObjs if hasattr(obj, 'attributeName')]
悸初 2024-07-11 00:00:03

使用列表理解会构建一个临时列表,如果要搜索的序列很大,它可能会耗尽您的所有内存。 即使序列不大,构建列表也意味着在 in 开始搜索之前迭代整个序列。

可以通过使用生成器表达式来避免临时列表:

foo = 12
foo in (obj.id for obj in bar)

现在,只要 bar 开头附近的 obj.id == 12 ,搜索就会很快,甚至如果 bar 无限长。

正如 @Matt 建议的那样,如果 bar 中的任何对象可能缺少 id 属性,则最好使用 hasattr

foo = 12
foo in (obj.id for obj in bar if hasattr(obj, 'id'))

Using a list comprehension would build a temporary list, which could eat all your memory if the sequence being searched is large. Even if the sequence is not large, building the list means iterating over the whole of the sequence before in could start its search.

The temporary list can be avoiding by using a generator expression:

foo = 12
foo in (obj.id for obj in bar)

Now, as long as obj.id == 12 near the start of bar, the search will be fast, even if bar is infinitely long.

As @Matt suggested, it's a good idea to use hasattr if any of the objects in bar can be missing an id attribute:

foo = 12
foo in (obj.id for obj in bar if hasattr(obj, 'id'))
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文