溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊(cè)×
其他方式登錄
點(diǎn)擊 登錄注冊(cè) 即表示同意《億速云用戶服務(wù)條款》

23argparse

發(fā)布時(shí)間:2020-07-05 05:22:28 來(lái)源:網(wǎng)絡(luò) 閱讀:265 作者:chaijowin 欄目:編程語(yǔ)言

?

argparse

?

習(xí)題:

實(shí)現(xiàn)ls命令功能,-l、-a、--all、-h選項(xiàng):

顯示路徑下的文件列表;

-a--all顯示包含.開(kāi)頭的文件;

-l,詳細(xì)列表顯示;

-h-l,人性化顯示文件大??;

c字符,d目錄,-普通文件,l軟鏈接,b塊設(shè)備,s socket文件,p pipe文件即FIFO;

按文件名排序輸出,可和ls的順序不一樣;

詳細(xì)列表顯示時(shí),時(shí)間按“年-- 時(shí)::秒”格式顯示;

?

-rw-r--r-- 1 root?? root??? 136 May? 7 09:45 test.json

?

mode 硬鏈接 屬主 屬組 字節(jié) 時(shí)間 文件名

?

?

?

?

?

?

參數(shù)分類:

ls -l /etc

位置參數(shù),參數(shù)放在那里,就要對(duì)應(yīng)一個(gè)參數(shù)位置,如/etc

選項(xiàng)參數(shù),必須通過(guò)前面是-短選項(xiàng)(短選項(xiàng)后面可以沒(méi)有參數(shù))或--長(zhǎng)選項(xiàng),然后后面的才算它的參數(shù),如-l;

?

程序或腳本在運(yùn)行時(shí),位置參數(shù)必須寫(xiě),argparse默認(rèn)的-h可有可無(wú);

?

argparse不僅僅做了參數(shù)的定義和解析,還自動(dòng)幫助生成了幫助信息,尤其是usage,可以看到自定義的參數(shù)是否是自己想要的;

?

?

源碼:

class ArgumentParser(_AttributeHolder, _ActionsContainer):

??? """Object for parsing command line strings into Python objects.

?

??? Keyword Arguments:

??????? - prog -- The name of the program (default: sys.argv[0])?? #程序的名字,缺省使用sys.argv[0]

??????? - usage -- A usage message (default: auto-generated from arguments)

??????? - description -- A description of what the program does?? #為程序功能添加描述

??????? - epilog -- Text following the argument descriptions

??????? - parents -- Parsers whose arguments should be copied into this one

??????? - formatter_class -- HelpFormatter class for printing help messages

??????? - prefix_chars -- Characters that prefix optional arguments

??????? - fromfile_prefix_chars -- Characters that prefix files containing

??????????? additional arguments

??????? - argument_default -- The default value for all arguments

??????? - conflict_handler -- String indicating how to handle conflicts

??????? - add_help -- Add a -h/-help option?? #自動(dòng)為解析器增加-h--help選項(xiàng),默認(rèn)為True

??? """

??? def __init__(self,

???????????????? prog=None,

???????????????? usage=None,

???????????????? description=None,

???????????????? epilog=None,

???????????????? version=None,

???????????????? parents=[],

???????????????? formatter_class=HelpFormatter,

???????????????? prefix_chars='-',

???????????????? fromfile_prefix_chars=None,

? ???????????????argument_default=None,

???????????????? conflict_handler='error',

???????????????? add_help=True):

?

?

??? def add_argument(self, *args, **kwargs):

??????? """

??????? add_argument(dest, ..., name=value, ...)

??????? add_argument(option_string, option_string, ..., name=value, ...)

??????? """

?

argparseadd_argument()action參數(shù),內(nèi)置6種動(dòng)作可在解析到一個(gè)參數(shù)時(shí)進(jìn)行觸發(fā):

store_true|store_false?? #保存相應(yīng)的布爾值,用于實(shí)現(xiàn)布爾開(kāi)關(guān)

store?? #默認(rèn),保存參數(shù)值,可能會(huì)先將參數(shù)值轉(zhuǎn)換成另一個(gè)數(shù)據(jù)類型,若沒(méi)顯式指定則為默認(rèn)

store_const?? #用于實(shí)現(xiàn)非布爾值的命令行標(biāo)記,保存一個(gè)被定義為參數(shù)規(guī)格的值

append?? #將值保存到一個(gè)列表中,若參數(shù)重復(fù)出現(xiàn),則保存多個(gè)值

append_const?? #將定義在參數(shù)規(guī)格中的值保存到一個(gè)列表中

version?? #打印關(guān)于程序的版本信息,然后退出

?

parser = argparse.ArgumentParser(prog='ls', add_help=True, description='list directory contents')

parser.add_argument('path', nargs='?', default='.', help='path help')

# parser.add_argument('-l')

# parser.add_argument('-l', nargs='?')

parser.add_argument('-l', action='store_true', help='use a long listing format')

parser.add_argument('-a', '--all', action='store_true', help='show all files,do not ignore entries starting with .')?? #長(zhǎng)短選項(xiàng)可同時(shí)給出

args = parser.parse_args()

print(args)

parser.print_help()

?

?

例:

tests.py

import argparse

?

parser = argparse.ArgumentParser()?? #獲得一個(gè)參數(shù)解析器

args = parser.parse_args()?? #分析參數(shù)

parser.print_help()?? #打印幫助

?

>python tests.py -h

usage: tests.py [-h]

?

optional arguments:

? -h, --help? show this help message and exit

?

?

例:

import argparse

?

parser = argparse.ArgumentParser(prog='ls', add_help=True, description='list directory contents')

parser.add_argument('path')?? #path為位置參數(shù),必須提供,否則報(bào)error: the following arguments are required

?

args = parser.parse_args()

print(args)

?

s>python tests.py

usage: ls [-h] path

ls: error: the following arguments are required: path

?

?

例:

import argparse

?

parser = argparse.ArgumentParser(prog='ls', add_help=True, description='list directory contents')

parser.add_argument('path')

?

args = parser.parse_args(('e:/',))?? #分析參數(shù),同時(shí)傳入可迭代的參數(shù),('/etc'.split())(('/etc'),)('/etc -all'.split())(('/etc/','-lah'));Namespace(path='e:/')里的path可通過(guò)Namespace對(duì)象訪問(wèn),如args.path

print(args)?? #打印名詞空間中收集的參數(shù)

?

>python tests.py

Namespace(path='e:/')

?

?

例:

import argparse

?

parser = argparse.ArgumentParser(prog='ls', add_help=True, description='list directory contents')

parser.add_argument('path', nargs='?', default='.', help='path help')?? #default,給path提供默認(rèn)值,當(dāng)前路徑,path也變成可選的;nargs表示這個(gè)參數(shù)接收結(jié)果參數(shù),?表示可有可無(wú);help表示幫助文檔中這個(gè)參數(shù)的描述

?

args = parser.parse_args()

print(args)

?

>python tests.py

Namespace(path='.')

?

?

?

-l-a的實(shí)現(xiàn):

?

parser.add_argument('-l')?? #效果為

Namespace(l=None, path='.')

usage: ls [-h] [-l L] [path]

?

parser.add_argument('-l', nargs='?')?? #效果為

Namespace(l=None, path='.')

usage: ls [-h] [-l [L]] [path]

?

parser.add_argument('-l', action='store_true')?? #效果為

Namespace(l=False, path='.')

usage: ls [-h] [-l] [path]

?

例:

parser = argparse.ArgumentParser(prog='ls', add_help=False, description='list directory contents')

parser.add_argument('path', nargs='?', default='.', help='path help')

parser.add_argument('-l', action='store_true', help='use a long listing format')

parser.add_argument('-a', '--all', action='store_true', help='show all files,do not ignore entries starting with .')

parser.add_argument('-h', action='store_true', help='making readable easily')

?

if __name__ == '__main__':

??? args = parser.parse_args()

??? print('args=', args)

??? # parser.print_help()

??? print(args.path, args.l, args.h, args.all)

?

>python tests.py -l -a .

args= Namespace(all=True, h=False, l=True, path='.')

. True False True

?

?

?

版本1

import argparse

from pathlib import Path

import datetime

?

import win_unicode_console

win_unicode_console.enable()

?

?

def _convert_mode(mode: int):

??? modelst = ['r', 'w', 'x', 'r', 'w', 'x', 'r', 'w', 'x']?? #modelst = list('rwx'*3)

??? modestr = bin(mode)[-9:]

??? # print(modestr)

??? ret = ''

??? for i, c in enumerate(modestr):

??????? if c == '1':

??????????? ret += modelst[i]

??????? else:

??????????? ret += '-'

??? return ret

?

def _convert_human(size: int):

??? # units =? [' ', 'K', 'M', 'G', 'T', 'P']?? # units = list(' KMGTP')

??? units = ' KMGTP'

??? depth = 0

??? while size >= 1000:

??????? size = size // 1000

??????? depth += 1

??? return '{}{}'.format(size, units[depth])

?

def _convert_type(file:Path):

??? ret = ''

??? if file.is_dir():

??????? ret = 'd'

??? elif file.is_symlink():

??????? ret = 'l'

??? elif file.is_socket():

??????? ret = 's'

??? elif file.is_block_device():

??????? ret = 'b'

??? elif file.is_char_device():

??????? ret = 'c'

??? else:

??????? ret = '-'

??? return ret

?

def showdir(path: str='.', detail=False, all=False, human=False) -> list:

??? p = Path(path)

??? for file in p.iterdir():

??????? # if not all:

??????? #???? if file.name.startswith('.'):

??????? #???????? continue

??????? if not all and file.name.startswith('.'):

??????????????? continue

?

??????? if detail:

??????????? st = file.stat()

????????? ??# print(st)?? #os.stat_result(st_mode=33206, st_ino=7599824371282335, st_dev=178462745, st_nlink=1, st_uid=0, st_gid=0, st_size=47, st_atime=1551941978, st_mtime=1551941978, st_ctime=1551928586)

??????????? h = str(st.st_size)

??????????? if human:

???? ???????????h = _convert_human(st.st_size)

??????????? # drwxr-xr-x 9 ane? ane? 4.0K Apr 11 02:40 apache-tomcat-7.0.67

??????????? # (33206, 1, 0, 0, 3031, 1557296696.6941395, 'tests.py')

??????????? # yield (st.st_mode, st.st_nlink, st.st_uid, st.st_gid, st.st_size, st.st_atime, file.name)

??????????? yield (_convert_type(file) + _convert_mode(st.st_mode), st.st_nlink, st.st_uid, st.st_gid, h,

?????????????????? datetime.datetime.fromtimestamp(st.st_atime).strftime('%Y-%m-%d %H:%M:%S'), file.name)

??????? else:

??????? # print(file.name)

??????????? yield file.name

?

# print(showdir.__annotations__)

?

parser = argparse.ArgumentParser(prog='ls', add_help=False, description='list directory contents')

parser.add_argument('path', nargs='?', default='.', help='path help')

parser.add_argument('-l', action='store_true', help='use a long listing format')

parser.add_argument('-a', '--all', action='store_true', help='show all files,do not ignore entries starting with .')

parser.add_argument('-h', action='store_true', help='making readable easily')

?

if __name__ == '__main__':

??? args = parser.parse_args()

??? print('args=', args)

??? # parser.print_help()

??? print('path={} -l={} -h={} -a={}'.format(args.path, args.l, args.h, args.all))

?

??? for file in showdir(args.path, detail=args.l, all=args.all, human=args.h):

??????? print(file)

?

?

版本2

1、使用stat模塊,

In [29]: help(stat.filemode)

Help on built-in function filemode in module _stat:

filemode(...)

??? Convert a file's mode to a string of the form '-rwxrwxrwx'

?

In [24]: p = Path('gis.log')

In [25]: p.stat

Out[25]: <bound method Path.stat of WindowsPath('gis.log')>

In [26]: p.stat()

Out[26]: os.stat_result(st_mode=33206, st_ino=1970324837080203, st_dev=178462745, st_nlink=1, st_uid=0, st_gid=0, st_size=70330, st_atime=1550905696, st_mtime=1550905642, st_ctime=1550905696)

In [27]: p.stat().st_mode

Out[27]: 33206

In [28]: stat.filemode(p.stat().st_mode)

Out[28]: '-rw-rw-rw-'

?

2、整合代碼,用到yield from

?

?

import argparse

from pathlib import Path

import datetime

import stat

?

import win_unicode_console

win_unicode_console.enable()

?

parser = argparse.ArgumentParser(prog='ls', add_help=False, description='list directory contents')

parser.add_argument('path', nargs='?', default='.', help='path help')

parser.add_argument('-l', action='store_true', help='use a long listing format')

parser.add_argument('-a', '--all', action='store_true', help='show all files,do not ignore entries starting with .')

parser.add_argument('-h', action='store_true', help='making readable easily')

?

?

def showdir(path: str='.',? detail=False, all=False, human=False) -> list:

??? # modelst = ['r', 'w', 'x', 'r', 'w', 'x', 'r', 'w', 'x']? # modelst = list('rwx'*3)

??? # def _convert_mode(mode: int):

??? #???? modestr = bin(mode)[-9:]

??? #???? # print(modestr)

??? #???? ret = ''

??? #???? for i, c in enumerate(modestr):

??? #???????? if c == '1':

??? #???????????? ret += modelst[i]

??? #???????? else:

??? #???????????? ret += '-'

??? #???? return ret

?

??? def _convert_human(size: int):

??????? # units =? [' ', 'K', 'M', 'G', 'T', 'P']?? # units = list(' KMGTP')

??????? units = ' KMGTP'

??????? depth = 0

??????? while size >= 1000:

??????????? size = size // 1000

??????????? depth += 1

??????? return '{}{}'.format(size, units[depth])

?

??? # def _convert_type(file:Path):

??? #???? ret = ''

??? #???? if file.is_dir():

??? #???????? ret = 'd'

??? #???? elif file.is_symlink():

??? #???????? ret = 'l'

??? #???? elif file.is_socket():

??? #???????? ret = 's'

??? #???? elif file.is_block_device():

??? #???????? ret = 'b'

??? #???? elif file.is_char_device():

??? #???????? ret = 'c'

??? #???? else:

??? #???????? ret = '-'

??? #???? return ret

?

??? def _showdir(path: str='.', detail=False, all=False, human=False) -> list:

??????? p = Path(path)

??????? for file in p.iterdir():

??????????? # if not all:

??????????? #???? if file.name.startswith('.'):

??????????? #???????? continue

??????????? if not all and file.name.startswith('.'):

??????????????????? continue

?

??????????? if detail:

??????????????? st = file.stat()

??????????????? # print(st)?? #os.stat_result(st_mode=33206, st_ino=7599824371282335, st_dev=178462745, st_nlink=1, st_uid=0, st_gid=0, st_size=47, st_atime=1551941978, st_mtime=1551941978, st_ctime=1551928586)

??????????????? h = str(st.st_size)

??????????????? if human:

??????????????????? h = _convert_human(st.st_size)

??????????????? # drwxr-xr-x 9 ane? ane? 4.0K Apr 11 02:40 apache-tomcat-7.0.67

??????????????? # (33206, 1, 0, 0, 3031, 1557296696.6941395, 'tests.py')

??????????????? # yield (st.st_mode, st.st_nlink, st.st_uid, st.st_gid, st.st_size, st.st_atime, file.name)

??????????????? # yield (_convert_type(file) + _convert_mode(st.st_mode), st.st_nlink, st.st_uid, st.st_gid, h,

?????????????????????? # datetime.datetime.fromtimestamp(st.st_atime).strftime('%Y-%m-%d %H:%M:%S'), file.name)

??????????????? yield (stat.filemode(st.st_mode), st.st_nlink, st.st_uid, st.st_gid, h,

?????????????????????? datetime.datetime.fromtimestamp(st.st_atime).strftime('%Y-%m-%d %H:%M:%S'), file.name)

??????????? else:

??????????? # print(file.name)

??????????????? yield file.name

?

??? yield from sorted(_showdir(path, detail, all, human), key=lambda x: x[len(x)-1])

?

# print(showdir.__annotations__)

?

if __name__ == '__main__':

??? args = parser.parse_args()

??? print('args=', args)

??? # parser.print_help()

??? print('path={} -l={} -h={} -a={}'.format(args.path, args.l, args.h, args.all))

?

??? for file in showdir(args.path, detail=args.l, all=args.all, human=args.h):

??????? print(file)

?

?

>python tests.py -lah .

args= Namespace(all=True, h=True, l=True, path='.')

path=. -l=True -h=True -a=True

('-rw-rw-rw-', 1, 0, 0, '47 ', '2019-03-07 14:59:38', '__init__.py')

('drwxrwxrwx', 1, 0, 0, '4K', '2019-04-02 17:15:21', '__pycache__')

('-rw-rw-rw-', 1, 0, 0, '209 ', '2019-03-07 14:42:00', 'admin.py')

('-rw-rw-rw-', 1, 0, 0, '1K', '2019-04-01 13:36:40', 'adminx.py')

('-rw-rw-rw-', 1, 0, 0, '119 ', '2019-03-07 14:59:03', 'apps.py')

('-rw-rw-rw-', 1, 0, 0, '854 ', '2019-03-27 15:12:48', 'forms.py')

('drwxrwxrwx', 1, 0, 0, '4K', '2019-03-07 13:46:16', 'migrations')

('-rw-rw-rw-', 1, 0, 0, '2K', '2019-03-28 16:32:33', 'models.py')

('-rw-rw-rw-', 1, 0, 0, '4K', '2019-05-08 16:05:48', 'tests.py')

('-rw-rw-rw-', 1, 0, 0, '786 ', '2019-03-28 16:10:02', 'urls.py')

('-rw-rw-rw-', 1, 0, 0, '9K', '2019-03-30 15:48:10', 'views.py')


向AI問(wèn)一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI