2012-05-02 147 views
1

这是我到目前为止有:鉴于任意收集,有没有办法判断它是否有序?

def is_ordered(collection): 
    if isinstance(collection, set): 
     return False 
    if isinstance(collection, list): 
     return True 
    if isinstance(collection, dict): 
     return False 

    raise Exception("unknown collection") 

是否有更好的方法来做到这一点?

注:我的意思是有序和不是排序。

动机:

我要遍历的有序集合。例如

def most_important(priorities): 
    for p in priorities: 
     print p 

在这种情况下,优先级排序的事实很重要。它不是什么样的收藏品。我想在这里住鸭子打字。我经常被Pythonistas的类型检查阻止。

+4

你的代码已经失败了'collections.OrderedDict'的实例 –

+0

和其他我假设的其他人。关键是,我是否需要测试每一个可能的集合,还是有更强大的方法来做到这一点? – cammil

+2

只需对其进行迭代,并确保调用者正在传递一个有序集合。 – Marcin

回答

4

如果收集真的是任意的(意味着它可以是任何类别的),那么答案必须是

基本上有两种可能的方法:

  1. 了解,可以呈现给你的方法每一个可能的类,并且无论是有序的;
  2. 通过插入每个可能的组合键来检查集合,并查看是否保留排序。

后者显然是不可行的。前者符合你已有的内容,除了你必须知道每个派生的类,例如collections.OrderedDict;检查dict是不够的。

坦率地说,我认为整个is_ordered检查是一个蠕虫的罐头。无论如何,你为什么要这么做?

+0

我可以放置的标准限制可能有用吗?还是应该像我一样采取课堂检查? – cammil

+0

@cammil为什么不仅仅指定使用人类语言(如英语)只需要传递订购集合,并检查您的调用代码以确保您能够做到这一点? – Marcin

+0

请参阅编辑。这是否回答你的问题? – cammil

-1

如果列表没有排序,例如[1,3,2]

+2

[1,3,2] _is_命令。它没有排序。 – cammil

+0

我不知道你是什么意思的“命令”呢?但我同意艾克斯写道 - 你真的不行。任何人都可以执行例如命令的“字典”。集合库中有一个OrderedDict类。 – uhz

+1

@uhzzre:取一个像“”你好“的字符串。它被命令(=字符顺序)。它没有排序,虽然它会是“ehllo”。 –

1

更新:从本质上讲,您试图单元测试传递给您的参数。停止这样做,然后单元测试你自己的代码。测试你的消费者(确保它与有序集合一起工作),然后单元测试调用它的代码,以确保它获得正确的结果。

在静态类型语言中,您只需将自己限制为特定类型。如果您真的想要复制它,只需指定您接受的唯一类型,然后测试这些类型。如果有其他事情通过,则引发异常。这不是Python的,但它可靠地实现你想要做什么


好了,你有两种可能的方法:

  1. 任何与append方法几乎可以肯定是有序的;和
  2. 如果它只有一个add方法,您可以尝试添加一个临时值,然后遍历该集合以查看临时值是否出现在末尾(或可能在一端);您可以尝试添加第二个随机数,然后再次执行,以增强自信。

当然,这不起作用,例如,该集合是空的,或者有一个排序函数不会导致在结尾添加。

也许更好的解决方案是简单地指定您的代码需要有序集合,并且只传递它的有序集合。

0

我认为枚举90%的情况与你将要得到的一样好(如果使用Python 3,用str替换basestring)。可能还需要考虑你会如何处理生成的表情和类似之流,太(再次,如果用PY 3,跳过xrangor):

generator = type((i for i in xrange(0))) 
enumerator = type(enumerate(range(0))) 
xrangor = type(xrange(0)) 
is_ordered = lambda seq : isinstance(seq,(tuple, list, collections.OrderedDict, 
              basestring, generator, enumerator, xrangor)) 

如果来电者开始使用itertools,那么你还需要添加itertools类型,由islice,imap,groupby返回。但这些特殊案例的数量真的开始指向code smell

相关问题