简体   繁体   English

用Python编写向量(数学)类

[英]Writing a Vector (Math) Class in Python

Here is my Vector class 这是我的Vector课

class Vector:
   def __init__(self, *v):
        self.v = v

It works great for things such as: 它适用于以下情况:

v = Vector(1, 1, 1)

where self.v prints out a list self.v打印出一个列表

How would I change it so that: 我将如何更改它,以便:

v = Vector([1, 1, 1]) 

it prints out a list. 它打印出一个列表。 Currently, it prints out a list within a list. 当前,它在列表中打印出一个列表。

from collections import Iterable

class Vector:
    def __init__(self, *v):
        if len(v) == 1 and isinstance(v[0], Iterable) and not isinstance(v[0], str):
            # iterable (but not string) - cast to list
            self.v = list(v[0])
        else:
            self.v = v

Since *v will give multiple positional argument, if you don't want to loose this property you can check it the length of v is 1 then just assign the first item to self.v : 由于*v将会给多个位置的说法,如果你不想失去这个属性,你可以检查它的长度, v为1,则只是将第一个项目self.v

class Vector:
   def __init__(self, *v):
        self.v = v[0] if len(v) == 1 else v 

Also note that this expression might raise some exceptions based on the type of v So as a more pythonic and safer way you better to use a try-except expression to handle the exceptions. 还要注意,此表达式可能会基于v的类型引发一些异常。因此,作为一种更Python化且更安全的方式,您最好使用try-except表达式来处理异常。

from collections.abc import Iterable # In python 2.x collections import Iterable

    class Vector:
       def __init__(self, *v):
            try:
                self.length = len(v)
            except TypeError:
                self.v = v
            else:
                 if isinstance(v, Iterable):
                     self.v = v[0] if self.length == 1 else v
                 else:
                     self.v = v

If you want your class to behave differently when it's passed a single list than when it's passed multiple numbers, you need to put some conditional logic in your __init__ method. 如果您希望类在传递单个列表时的行为不同于传递多个数字时的行为,则需要在__init__方法中放入一些条件逻辑。 Something like this might work (though there are other ways you could do the checking): 这样的事情可能会起作用(尽管您可以通过其他方法进行检查):

def __init__(self, *v):
    if len(v) == 1:
        v = v[0]

    self.v = v

Obviously this won't work as expected for a 1-dimensional Vector ( v will be set to the single scalar value, rather than a 1-valued list). 显然,这对于一维向量不起作用( v将设置为单个标量值,而不是一值列表)。 You could probably use isinstance to make sure the single value is in fact a list or tuple if you want, but I suspect there would still be awkward corner cases you'd get wrong. 如果需要的话,您可以使用isinstance来确保单个值实际上是列表或元组,但是我怀疑仍然会遇到一些尴尬的错误情况。

A better approach may be to change the code that wants to pass in a list. 更好的方法可能是更改要传递到列表中的代码。 If instead of Vector([1,1,1]) , you did Vector(*[1,1,1]) , your existing code would work just fine. 如果您使用Vector(*[1,1,1])代替Vector([1,1,1]) ,那么您现有的代码就可以正常工作。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM