python返回自定义对象

时间:2018-04-07 22:49:27

标签: python object

很久以来.NET程序员,新手Python学习者。

在.NET中,如果您想从数据库中获取客户记录并对UI中的信息执行某些操作,您可以这样做

Customer customer = ReadCustomerRecord (12345)

客户是一个自定义对象,包含有关客户的几十个字段。 ReadCustomerRecord连接到数据库读取记录并填充Customer对象中的字段,然后返回它。

现在,我不明白你是如何在Python中做同样的事情的。如果我只是从正在进行初始化的方法返回customer对象,那么如何告诉代码它是什么类型的对象?

2 个答案:

答案 0 :(得分:1)

查看Python类。

实施例

class Customer:
    #constructor, self == this
    def __init__(self, data):
         self.data = data

def ReadCustomerRecord (cust_id):
    ## get from db
    cust = Customer(data)
    return cust

customer = ReadCustomerRecord(1234)

Python是一种动态类型语言,意味着在程序运行期间完成类型检查。所有类型都是隐式的,实际上方法可以根据条件返回不同的类型。

def func(is_list):
    if is_list:
        return [1,2,3]
    else:
        return 1

答案 1 :(得分:1)

首先,如果你需要,Python 可以选择静态输入。语法与C#略有不同,但它与许多其他语言相同:

customer: Customer = ReadCustomerRecord(12345)

如果你然后通过Mypy或其他静态类型检查器或分析器运行你的代码(许多IDE已经集成,所以你不必做任何事情),它将能够验证你唯一的事情永久存储在customer中的是Customer类型的值,您永远不会对它进行任何对该类型的值不合法的事情。

但是,即使您使用静态类型检查,也不需要指定每个变量的类型,因为大多数变量都可以自动推断。同样,这与C#不同,但它与许多其他语言相同 - 包括具有更严格规则的静态类型语言和比C#更强大的类型系统,如Swift,Rust或F#。

"推理"意味着如果您没有指定类型,静态检查器会发现customer必须是Customer,因为ReadCustomerRecord返回的是auto。然后它可以像以前一样验证所有相同的东西。

就像在Swift或Go中一样,它在Python中的惯用语不指定变量的类型,除非它要么显示一些非显而易见的东西,要么对人类读者有帮助,或者解决一些模糊不清的东西。静态检查器。

在现代语言中,它实际上只是C系列中的语言(C,C ++,Java,C#等),它们要求您按名称指定所有内容的类型,即使它的名称也是如此。令人目眩的显而易见 - 甚至其中很多都会给你Any这样的东西,可以用来告诉编译器推断出类型。

但是Python和我提到的其他语言之间的最大区别是Python是动态类型的。静态检查器可以验证您的变量类型,但实际的编译器和解释器并不关心它们。事实上,在幕后,变量根本就没有类型。

在Python中,它的具有类型。变量只是值的名称,并且在不同时间为不同类型的不同值重用相同的名称是完全合法的(有时是惯用的)。

静态检查可以证明您认为自己没有使用动态功能,并且当您需要这些动态功能时它会不受影响。

有时候,你需要静态检查一堆相关的东西,但你有一个变量,你依赖于鸭子打字。为此,您可以通过将其称为customer = ReadCustomerRecord(12345) 来选择该变量,即使您选择加入该变量也是如此。

所以,您可能只想将该行写为:

customer: Customer = ReadCustomerRecord(12345)

但如果读者不清楚这是什么类型,你可以这样做:

customer

如果您需要使用customer: Any = ReadCustomerRecord(12345) 进行鸭子打字,但静态类型检查周围的其他所有内容:

#include <vector>
#include <iostream>
//dummy class
struct Card{
    int x; 
};

class Hand{
 public: 
    Hand(){}
    std::vector<Card> handV;
    virtual ~Hand(){}        
    virtual void getCard(Card k) 
    {
        handV.push_back(k);
    }
    virtual void showHand() 
    {
        for(std::vector<Card>::const_iterator it = handV.begin(); 
            it != handV.end(); 
            it++) 
        std::cout << it->x << " ";
    }
};
class HandMaster: public Hand
{
    public:
    HandMaster(){} 
    //add additional methods
};

class HandOther: public Hand
{
    public:
    HandOther(){} 
    //add additional methods
};

class Deck
{
public:
    std::vector<Card> deck;
    Deck(){
        Card c;
        for(int i = 1; i <= 52; ++i){
            c.x = i; 
            deck.push_back(c);
        }
    }
    void passCard(Hand *x)
    {
        x->getCard(deck.back());
        deck.pop_back();
    }
};

int main()
{
    Deck d;
    Hand* p = new Hand();
    HandMaster *m = new HandMaster();
    HandOther * o = new HandOther();
    for(int i =0; i < 5; ++i){
        d.passCard(p); 
        d.passCard(m); 
        d.passCard(o); 
    }
    std::cout << "\nHand:";
    p->showHand();
    std::cout << "\nHandMaster:";
    m->showHand();
    std::cout << "\nHandOther:";
    o->showHand();

    std::cout << "\n";
    delete o;
    delete p;
    delete m;
}