欢迎各位兄弟 发布技术文章

这里的技术是共享的

You are here

Python的from import和import的区别?

我刚开始学习Python,对于import和from import我觉得应该是有区别的,但是在网上搜了一圈,还是没有解答我的疑惑。
ps:我是使用的python3.5版本。
例如datetime:

from datetime import datetime
print(datetime.now())
就可以执行,但是用import就不行:
import datetime
print(datetime.now())
报错:AttributeError: module 'datetime' has no attribute 'now'
import datetime.datetime 
print(datetime.now())

报错:ImportError: No module named 'datetime.datetime'; 'datetime' is not a package
//应该此时 print(datetime.datetime.now()) 是对的  

是不是datetime只能用from import而不能用import?
from import 和 import有什么区别?
关注者
146
 
被浏览
35034
 

23 个回答

两个import语义有差异
import datetime
print(datetime.datetime.now())
是引入整个datetime包
from datetime import datetime
print(datetime.now())

是只引入datetime包里的datetime类

所以import之后前者是datetime这个包可见 后者是datetime.datetime这个类可见

from import : 从车里把矿泉水拿出来,给我
import : 把车给我

题主可能困惑于,为什么会有人让自己把“车里面的车”拿出来,因为这是俩不同的车啊,里面那个是玩具车

我想楼主容易搞错的原因是用了datetime的包。
datetime的包里还有个重名的datetime的子项,在这个子项下才有now的函数。
因为有个重名的子项,所以初学者可能会搞混。
把楼主的疑问换个包来回答楼主应该能清晰点:
下面三个都是正确的写法,调用的是os包里path子项的join函数,作用是将路径相加成一个完整路径:

from os.path import join
print(join('C:\\windows', 'system32'))

import os
print(os.path.join('C:\\windows', 'system32'))

import os.path
print(os.path.join('C:\\windows', 'system32'))
输出全是:
C:\windows\system32

你虽然import datetime,但是now是datetime模块下datetime类的now方法,所以你要写成datetime.datetime.now啊……

from datetime import datetime是因为从datetime里引入了datetime类,引入的并不是这个模块而是这个类,自然是datetime.now
import xx导入模块对于模块中的函数,每次调用需要“模块.函数”来用。
from xx import fun 直接导入模块中某函数,直接fun()就可用。
告诉你大法:from xx import * 该模块中所有函数可以直接使用。
====================2016-12-11=========更新===========
觉得之前的回答不够全面,再补充下吧!
题主应该把import xx,xx不只想象成一个单文件,它还可能是一个文件夹(所谓的包),
文件夹里面还有子文件夹。你的问题是一级文件夹与二级文件夹同名而已。你是调用深度不够。
举一反三多几次就明白了。

一般情况下尽量使用import a,此时访问B时,可以通过a.B的形式。

有节制的使用from a import B,这样可以直接使用B。

避免使用from a import *,这种方法会污染命名空间,而且不能直观的显示导入哪些对象
你有一个工具箱,箱子里有剪刀,有钳子,有螺丝刀等等。
现在你想拧螺丝。
然后你一个操作是:从 工具箱 里拿 螺丝刀,然后用 螺丝刀 拧螺丝 ( from import)。
别一个操作是: 拿了 工具箱 ,没打开呢,直接就去 拧螺丝 ( import )

import Module # 引入模块
from Module import Other # 引入模块中的类、函数或者变量
from Module import * # 引入模块中的所有‘公开’成员

PS:当有一个包名为pname时,其内部 *.py 文件的模块名就是 pname.* 也就是说模块名中包含了 Package包 这个概念。

其区别就是:
第一个:引入的模块(假如是 mdemo )会自动生成一个‘对象‘以模块名命名,然后就可以通过这个‘对象’(mdemo)获取该模块里面的类、函数或变量等...
第二个:引入模块中的Other(这里的Other就是模块中定义的成员)成员,调用时就可以省略 模块名。
第三个:这种情况如果上面的第二个弄懂的话就不难理解了,其意思就是引入模块中所有'公开'的成员。

---------鉴于题主的提问可以快速套用上面的分析:
from datetime import datetime
# 引入 datetime 模块中的 datetime 类,然后就可以通过datetime这个类调用now() 方法了
# 即,内部可以通过datetime.now()来调用

import datetime
# 引入datetime 模块,然后通过这个模块来调用模块中的类datetime和类datetime中的方法now()
# 即:内部可以通过datetime.datetime.now()来调用

也就是说,有一个模块datetime,这个模块中有一个类datetime,在这个类中有一个方法now()
我们可以验证上面这句话是否正确:
我们可以通过查看python默认查找模块位置,一个个打开看下是否有datetime这个模块

----以上纯属我的理解,如有错误,多多指教

假如是import的话,后面大概是要这样导入的


比如说 import urllib2
这个时候后你要是调用包里面的方法就需要带上包名
比如说 urllib2.urlopen()

而,假如你是只想导入这个包里的某个方法(又或者全部)

from urllib2 import urlopen
这样的话以后就可以直接使用urlopen方法了
urlopen()


总结一下,这两个的区别给我的感觉就是假如你需要明确这个方法从哪个包来就只用import,这样看起来会更容易理解,而,假如你不需要让代码看起来尽量简单那么就使用from import 这样就不需要前缀包名,代码看起来也比较清爽,
至于你的datetime很容易知道,你的包名和其中一个方法同名,你以为引入了datetime方法,而实际却只导入了包,所以使用方法应该是datetime.datetime.now()


小白一枚,如有什么问题还请大家多多指教⁽⁽ ( ´͈ ᗨ `͈ ) ⁾⁾
from datetime import datetime
这行命令相当于,校长说:高三二班的 李伟出来,站在我面前

import datetime
这行命令相当于,校长说:高三二班,都站在我面前


from datetime import datetime 中 调用 datetime.now() 成功是因为:

这个命令相当于,校长说:: 李伟,现在是几点? 因为就一个李伟站在他面前,能确定是哪个李伟。

import datetime 调用 datetime.now() 失败是因为:

这个命令相当于,校长说:: 李伟,现在是几点? 可是校长面前,站了整个高三二班,没法知道是哪个李伟?? datet

from module import Something

module是一个模块,说白了是一个文件,比如 datetime.py文件。
Something是模块的一个具体对象,可以是函数,可以是变量,可以是类。

Python标准库中有些东西容易糊弄住新手,比如你说的datetime模块,datetime模块中有一个与datetime.py文件同名的类 <datetime>,now是它的一个静态方法,可以不用生成实例直接以Class.method()的方式调用。

为什么datetime模块中要定义一个同名的类糊弄人,这个我也不清楚,可能门亲吻了脑子。Python的标准库中还有几个同样不规范的模块。
当你用from datetime import datetime时,是从datetime包中导入datetime类,用的时候直接可以引用datetime。import datetime的话是导入整个datetime包,引用包里的类时要用datetime.xxx

解决两个问题即可搞清楚两者的异同

1、import后面可以跟什么

1)可以跟文件名、目录名(当然最好理解为包名),这样就类似include 这样的语句,将文件加入而已。

import example1.example1_1 #这里就是将example1/example1_1.py 引入

或者可以使用from

from example1 import example1_1

从这里可以看出,如果从引入文件的角度出发,from后面的内容和import后面的内容相似,都是文件名或者目录名。这种方式,的确不容易判断example1_1到底是一个文件、目录或是example1_1()这样一个方法。

调用的时候,必须按照import后面的包的完整结构进行调用

example1_1.say_hello()

 

2)可以跟类名、方法名

from example1.example1_1 import say_hello #从目录、包或文件中引入一个方法

say_hello() #可以直接调用;

from example1.example1_1 import User #从目录、包或者文件中引入一个类

User('name'='xiaoming')#可以直接调用

 

2、from后面可以跟什么

只能是文件、目录或者包。

 

推荐的写法,使用“from 包名 import 方法/类”然后直接调用方法或者类的书写方式。

当然,如果import只是将整个文件包进来,仅作文件的连接,两种方式就没有什么区别。

因为一个模块里面 可以有函数,也可以有类,也可以有常量等等(其他的东西我暂时还不知道...)。

这个类里面,又可以有函数。

 

你引入的datetime模块 里面 有 一个类 和 datetime模块 名字是一样的,就是datetime类

而这个now() 函数是在datetime类里的,而不是直接在datetime模块下的。

所以你当你引入(import) datetime 这个模块,是把整个模块引入了。所以这个时候调用这个now()函数的方式是这样的:

import datetime
print( datetime.datetime.now() )

 

而当你单独从(from) datetime 这个模块 引入(import) datetime 这个类 时。调用的方式是这样的:

from datetime import datetime
print( datetime.now() )

 

如有错误请指正

以上

楼上基本都回答完了,但是需要注意的是:

1.导入模块会创建新的模块命名空间,在调用导入模块中的函数时会引用该模块的命名空间。

2.from ** import **是将模块里的具体定义加载到当前命名空间。

3.除非python已经用得666了,请尽量不要使用from module import * 。

楼主是不是从Java之类的语言转过来的?Java的import看上去和Python里不太一样,Java里没有import一个包名的概念(或者说极少用),而在Python里这种用法较常见。所以会觉得怎么明明已经import了一个东西,使用起来的时候还要加上前缀,其实你把它们都看成是命名空间就好了。解释器也需要足够的信息才能唯一确定一个类或者方法的具体调用是指哪,人确定不了的,它也确定不了
>>> from datetime import datetime as datetime1
>>> import datetime as datetime2
>>> datetime1 == datetime2
False
>>> datetime1 == datetime2.datetime
True
所以如果想通过datetime2来获得现在的时间,就要这样写
>>> datetime2.datetime.now()
datetime.datetime(2016, 3, 17, 9, 21, 31, 805042)

from datetime import datetime
print datetime.now()

import datetime
print datetime.datetime.now()

都是可以的。
python建议后者,显式优于隐式。
比如你有两个model都含有一个同名的method。
from model1 import method之后再执行
from model2 import method
model1中的method就被覆盖了。
如果是:
import model1
import model2
model1.method
model2.method
都可以执行。
import datetime
print(datetime.datetime.now())

还可以这样用:
from datetime import datetime as shijian
print(shijian.now())

我觉得Python还是比较接近自然语言的
导入部分和导入全部的差距,from还可以和as一同使用,可以

就好比如说,朋友有一把枪,你只想要他的枪去打猎,那就用import,import是把对方的枪给要过来,注意,是枪这个是整体;

可如果你是想要几发子弹装逼,那就没必要用枪了,用枪挺麻烦的,还不会使用,一不小心走火就悲剧了,所以这个时候你需要从枪里把子弹拿出来,注意,是需要里面的子弹,但是子弹在枪里,我不摸枪拿不到子弹呀,你朋友也不能用枪把子弹打出来,也就意味着,必须从枪里把子弹拿出来。

所以,from 枪 import 子弹,这个意思就是我需要枪里的子弹装逼。

你查一下name space的逻辑就明白了

我认为:

from xx import yyyy

是从xxx拿出yyyy

可以理解为

import yyyy.xx as zz

即从yyyy中拿出xx,命名为zz

区别在于,从柜子里拿出一个盒子和从柜子里拿出东西。东西指盒子和其他在柜子里的物品。

来自 https://www.zhihu.com/question/38857862
普通分类: