#python用下划线作为变量前缀和后缀指定特殊变量。稍后我们会发现,  
#对于程序来说,其中的有些变量是非常有用的,而其他的则是未知或者无用的。  
#我们总结一下Python中下划线的特殊用法  
#_xxx:不用'from module import *'导入  
#__xxx__:系统定义的名字  
#__xxx:类中的私有变量名

1.__name__

#__name__指示模块应该如何被加载
#由于主程序代码无论模块是被直接执行都会运行,我们必须知道模块如何决定运行方向。
#一个应用程序可能需要导入另个引用程序的一个模块,以便重用一些有用的代码。
#这种情况下,你只想访问那些位于其它应用程序中的代码,而不是像运行那个应用程序。
#因此一个问题产生了,"Python"是否有一种方法能在运行时检测该模块是被导入还是直接被执行呢?
#__name__系统变量就是正确的答案
#如果模块是被导入,__name__的值为模块名字
#如果模块是被直接执行,__name__的值为'__main__'

if __name__ == '__main__':
    main()

以上代码表示只有在此文件执行时才会调用main()函数,其他时候则不会执行。

2.__file__

用__file__ 来获得脚本所在的路径是比较方便的,但这可能得到的是一个相对路径,比如在脚本test.py中写入:

#!/usr/bin/env python
print __file__

按相对路径./test.py来执行,则打印得到的是相对路径,
按绝对路径执行则得到的是绝对路径。
而按用户目录来执行(~/practice/test.py),则得到的也是绝对路径(~被展开)

所以为了得到绝对路径,我们需要 os.path.realpath(__file__)。

3.__doc__

文档字符串。一般而言,是对函数/方法/模块所实现功能的简单描述。但当指向具体对象时,会显示此对象从属的类型的构造函数的文档字符串。


'''
本文件__doc__输出
'''
if __name__=='__main__':
print(__doc__) # print globals()['__doc__']
Login_User = {"is_login":False} def check_login(func):
"""
此处为函数__doc__变量输出值
:param func:
:return:
"""
def chk_inner(*args,**kwargs):
if Login_User["is_login"]:
func()
else:
print('请登录')
return chk_inner
print(check_login.__doc__) # 输出结果
本文件__doc__输出 此处为函数__doc__变量输出值
:param func:
:return:

4.__package__  和 __name__ 类似,当自己调用的时候返回none,当通过导入操作后输出文件所在的目录名

import os,sys
from lib import class6
BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
sys.path.append(BASE_DIR)
print(__package__)
print(class6.__package__) # 输出
None
lib

hasattr(object, name)

说明:判断对象object是否包含名为name的特性(hasattr是通过调用getattr(ojbect, name)是否抛出异常来实现的)。

参数object:对象。

参数name:特性名称。

示例:

>>> hasattr(list, 'append')
True >>> hasattr(list, 'add')
False
getattr()
getattr()函数是Python自省的核心函数,具体使用大体如下:

获取对象引用getattr
Getattr用于返回一个对象属性,或者方法


    1. class A:
    2. def __init__(self):
    3. self.name = 'zhangjing'
    4.     #self.age='24'
    5. def method(self):
    6. print"method print"
    7. Instance = A()
    8. print getattr(Instance , 'name, 'not find') #如果Instance 对象中有属性name则打印self.name的值,否则打印'not find'
    9. print getattr(Instance , 'age', 'not find')   #如果Instance 对象中有属性age则打印self.age的值,否则打印'not find'
    10. print getattr(a, 'method', 'default')
    11. #如果有方法method,否则打印其地址,否则打印default
    12. print getattr(a, 'method', 'default')()
    13. #如果有方法method,运行函数并打印None否则打印default
 

sys.modules

与其它任何 Python 的东西一样,模块也是对象。只要导入了,总可以用全局 dictionary sys.modules 来得到一个模块的引用。
 是一个字典,它包含了从 Python 开始运行起,被导入的所有模块。键字就是模块名,键值就是模块对象。请注意除了你的程序
导入的模块外还有其它模块。Python 在启动时预先装入了一些模块,如果你在一个 Python IDE 环境下,sys.modules 包含了你
在 IDE 中运行的所有程序所导入的所有模块。 反射

反射的作用就是列出对象的所有属性和方法,反射就是告诉我们,这个对象到底是什么,提供了什么功能 。

举个例子:

>>> import json
>>> dir(json)             
['JSONDecoder', 'JSONEncoder', '__all__', '__author__', '__builtins__', '__doc__', '__file__', '__name__', '__package__', '__path__', '__version__', '_default_decoder', '_default_encoder', 'decoder', 'dump', 'dumps', 'encoder', 'load', 'loads', 'scanner']
>>>

如上所看,dir 是一个内置的 反射函数 ,可以列出对象的属性和方法。

再看另外一个内置的方法 :getattr

>>> getattr(json,'encoder')
<module 'json.encoder' from '/usr/lib/python2.7/json/encoder.pyc'>
>>> getattr(json,'load')
<function load at 0x7f66af736140>
>>>

可以取出指定属性

再看另外一个方法 :callable

>>> callable(getattr(json,'load'))
True
>>> callable(getattr(json,'encoder'))
False
>>>

检查属性是否是可以调用的函数 。

了解基础之后,就需要考虑,它存在的价值在哪里了?

考虑一个应用的场景:IDE的自动补全。

在IDE中可以这样做:

>>> methodList = [attr for attr in dir(json)  if callable(getattr(json,attr))]
>>> methodList
['JSONDecoder', 'JSONEncoder', 'dump', 'dumps', 'load', 'loads']
>>>

>>> getattr(json,'load').__doc__
'Deserialize ``fp`` (a ``.read()``-supporting file-like object containing\n    a JSON document) to a Python object.\n\n    If the contents of ``fp`` is encoded with an ASCII based encoding other\n    than utf-8 (e.g. latin-1), then an appropriate ``encoding`` name must\n    be specified. Encodings that are not ASCII based (such as UCS-2) are\n    not allowed, and should be wrapped with\n    ``codecs.getreader(fp)(encoding)``, or simply decoded to a ``unicode``\n    object and passed to ``loads()``\n\n    ``object_hook`` is an optional function that will be called with the\n    result of any object literal decode (a ``dict``). The return value of\n    ``object_hook`` will be used instead of the ``dict``. This feature\n    can be used to implement custom decoders (e.g. JSON-RPC class hinting).\n\n    ``object_pairs_hook`` is an optional function that will be called with the\n    result of any object literal decoded with an ordered list of pairs.  The\n    return value of ``object_pairs_hook`` will be used instead of the ``dict``.\n    This feature can be used to implement custom decoders that rely on the\n    order that the key and value pairs are decoded (for example,\n    collections.OrderedDict will remember the order of insertion). If\n    ``object_hook`` is also defined, the ``object_pairs_hook`` takes priority.\n\n    To use a custom ``JSONDecoder`` subclass, specify it with the ``cls``\n    kwarg; otherwise ``JSONDecoder`` is used.\n\n    '
>>>

大概就明白了 反射的功能了。

#-*- coding:utf8 -*-

class Obj :
    """ An object that use reflection """

def __init__(self,name):
        """ 构造函数 """
        self.name = name

def echo_methods(self):
        """ 输出类中所有的方法,以及doc 文档 """
        print "\n Method List: "
        for attrName in dir(self):
            attr = getattr(self,attrName)
            if callable(attr):
                print attrName,"():",attr.__doc__

def echo_attributes(self):
        print "\n Attributes"

for name in dit(self):
            attr = getattr(self,attr)
            if not callable(attr):
                print name,":",attr

obj = Obj("testObject")
obj.echo_methods()

ubuntu@yee:/tmp$ python ref.py

Method List:
__init__ ():  构造函数
echo_attributes (): None
echo_methods ():  输出类中所有的方法,以及doc 文档

可以看到,通过反射,我们可以知道类中所有的方法以及方法的属性和注释文档信息。

内置函数__import__

我们知道import语句是用来导入外部模块的,当然还有from...import...也可以,但是其实import实际上是使用builtin函数__import__来工作的。
    在一些程序中,我们可以动态地去调用函数,如果我们知道模块的名称(字符串)的时候,我们可以很方便的使用动态调用。

  1. import glob,os
  2. modules = []
  3. for module_file in glob.glob("*-plugin.py"):
  4. try:
  5. module_name,ext = os.path.splitext(os.path.basename(module_file))
  6. module = __import__(module_name)
  7. modules.append(module)
  8. except ImportError:
  9. pass #ignore broken modules
  10. #say hello to all modules
  11. for module in modules:
  12. module.hello()
 导入其他目下的模块:
   使用参数  fromlist=True,进行字符串拼接。
 

递归

递归(recursion):程序调用自身的编程技巧。
  递归满足2个条件:
    1)有反复执行的过程(调用自身)
    2)有跳出反复执行过程的条件(递归出口)

(1)阶乘
         n! = n * (n-1) * (n-2) * ...* 1(n>0)

def recursion(x):
if x == 1:
y = 1
else:
y = x * recursion(x - 1)
return y print(recursion(5))

(2)斐波那契数列

斐波纳契数列,又称黄金分割数列,指的是这样一个数列:1、1、2、3、5、8、13、21、……

这个数列从第三项开始,每一项都等于前两项之和。

有趣的兔子问题:

一般而言,兔子在出生两个月后,就有繁殖能力,一对兔子每个月能生出一对小兔子来。如果所有兔子都不死,那么一年以后可以繁殖多少对兔子?

分析如下:

第一个月小兔子没有繁殖能力,所以还是一对;

两个月后,生下一对小兔子,总数共有两对;

三个月以后,老兔子又生下一对,因为小兔子还没有繁殖能力,总数共是三对;

…… 

依次类推可以列出下表:

def fibo(n):
if n == 0:
return 0
if n == 1:
return 1
if n > 1:
return fibo(n - 1) + fibo(n - 2) print(fibo(4))
 
 
 
 

循序渐进Python3(六) -- 初识内置变量、反射、递归的更多相关文章

  1. Makefile内置变量,递归式变量,直接展开式变量,条件赋值,追加赋值

    将shell命令的输出赋值给变量: VALUE = $(shell   命令) Makefile中给变量赋值: =     是递归展开式变量 value1 = 5 value2 = $(value1) ...

  2. Python每日一练------内置函数+内置变量+内置模块

    1.内置函数 Python所有的内置函数     Built-in Functions     abs() divmod() input() open() staticmethod() all() e ...

  3. python3.7.1 内置函数

    python3.7.1 内置函数列表 内置函数 abs() delattr() hash() memoryview() set() all() dict() help() min() setattr( ...

  4. Maven系列三Maven内置变量

    Maven内置变量说明: ${basedir} 项目根目录(即pom.xml文件所在目录) ${project.build.directory} 构建目录,缺省为target目录 ${project. ...

  5. Maven的内置变量

    Maven内置变量说明: ${basedir} 项目根目录(即pom.xml文件所在目录) ${project.build.directory} 构建目录,缺省为target目录 ${project. ...

  6. nginx的那些内置变量

    nginx在配置文件nginx.conf中可以使用很多内置变量,配置如下: location /info { add_header 'Content-Type' 'text/html'; echo & ...

  7. Maven内置变量说明

    Maven内置变量说明: ${basedir} 项目根目录 ${project.build.directory} 构建目录,缺省为target ${project.build.outputDirect ...

  8. 学习笔记——Maven 内置变量

    Maven内置变量说明: ${basedir} 项目根目录(即pom.xml文件所在目录) ${project.build.directory} 构建目录,缺省为target目录 ${project. ...

  9. makefile 分析 -- 内置变量及自动变量

    makefile 分析1  -p 选项,可以打印出make过程中的数据库, 下面研究一下内置的变量和规则. -n 选项, 只运行,不执行, -d 选项,相当于--debug=a,  b(basic), ...

随机推荐

  1. Objective-c——UI基础开发第十二天(相册展示)

    一.知识点 模仿新特性 UICollectionViewFlowLayout自定义布局 相册 瀑布流(淘宝购物之类的 二.复习 a.UICollectionView 和 tableview共享一套AP ...

  2. Jocket

    https://docs.oracle.com/cd/E13150_01/jrockit_jvm/jrockit/geninfo/diagnos/diagnosTOC.html https://blo ...

  3. 【Unity3D基础教程】给初学者看的Unity教程(二):所有脚本组件的基类 -- MonoBehaviour的前世今生

    作者:王选易,出处:http://www.cnblogs.com/neverdie/ 欢迎转载,也请保留这段声明.如果你喜欢这篇文章,请点[推荐].谢谢! 引子 上一次我们讲了GameObject,C ...

  4. maven项目修改java编译版本的方式

    背景 使用 maven 3.x 安装到本地后,创建的项目一般都是基于JDK1.5版本.而目前大多数的项目已经升级到1.6或以上,尤其是Servlet3.0 已经要求Java6或以上版本的环境,往往需要 ...

  5. moment.js 的简单应用

     moment.js :时间处理的组件 例子:moment.html <!DOCTYPE html> <html> <head> <title>mome ...

  6. 【python】模块作用域

    作用域 在一个模块中,我们可能会定义很多函数和变量,但有的函数和变量我们希望给别人使用,有的函数和变量我们希望仅仅在模块内部使用.在Python中,是通过_前缀来实现的. 类似_xxx和__xxx这样 ...

  7. 每天一个 Linux 命令(8):cp 命令

    cp命令用来复制文件或者目录,是Linux系统中最常用的命令之一.一般情下,shell会设置一个别名,在命令行下复制文件时,如果目标文件已经存在,就会询问是否覆盖,不管你是否使用-i参数.但是如果是在 ...

  8. jquery 监听radio选中,取值

    $(document).ready(function(){ $("input[name=discount]").each(function(){ $(this).click(fun ...

  9. 36. Construct Binary Tree from Inorder and Postorder Traversal && Construct Binary Tree from Preorder and Inorder Traversal

    Construct Binary Tree from Inorder and Postorder Traversal OJ: https://oj.leetcode.com/problems/cons ...

  10. 49. Search in Rotated Sorted Array && Search in Rotated Sorted Array II

    Search in Rotated Sorted Array Suppose a sorted array is rotated at some pivot unknown to you before ...