九、Python Standard Library
1、Paths
from pathlib import Path
# Windows
Path("C:\\Program Files\\Microsoft")
# Or
Path(r"C:\Program Files\Microsoft")
# Mac
Path("/usr/local/bin")
Path() # Current
Path("ecommerce/__init__.py") # Subfolder
Path() / "ecommerce" / "__init__.py" # Combine: pathlib重载了除法运算符
Path.home() # get the home directory of the current user???
from pathlib import Path
path = Path("ecommerce/__init__.py")
path.exists()
path.is_file()
path.is_dir()
print(path.name)
print(path.stem)
print(path.suffix)
print(path.parent)
path1 = path.with_name("file.txt")
print(path1.absolute())
path2 = path.with_suffix(".txt")
print(path2)
__init__.py
__init__
.py
ecommerce
/Users/XXX/PycharmProjects/pythonProject1/ecommerce/file.txt
ecommerce/__init__.txt
2、Working With Directories
path.iterdir(): get the list of files and directories
from pathlib import Path
path = Path("ecommerce")
for p in path.iterdir():
print(p)
print("========================")
paths = [p for p in path.iterdir()]
print(paths)
print("========================")
paths = [p for p in path.iterdir() if p.is_dir()]
print(paths)
ecommerce/shopping
ecommerce/__init__.py
ecommerce/__pycache__
ecommerce/customer
========================
[PosixPath('ecommerce/shopping'), PosixPath('ecommerce/__init__.py'), PosixPath('ecommerce/__pycache__'), PosixPath('ecommerce/customer')]
========================
[PosixPath('ecommerce/shopping'), PosixPath('ecommerce/__pycache__'), PosixPath('ecommerce/customer')]
from pathlib import Path
path = Path("ecommerce")
py_files = [p for p in path.glob("*.py")]
print(py_files)
print("========================")
py_files = [p for p in path.rglob("*.py")]
print(py_files)
[PosixPath('ecommerce/__init__.py')]
========================
[PosixPath('ecommerce/__init__.py'), PosixPath('ecommerce/shopping/sales.py'), PosixPath('ecommerce/shopping/__init__.py'), PosixPath('ecommerce/customer/__init__.py'), PosixPath('ecommerce/customer/contact.py')]
3、Working With Files
from pathlib import Path
from time import ctime
path = Path("ecommerce/__init__.py")
# path.exists()
# path.rename("init.txt")
# path.unlink()
print(ctime(path.stat().st_ctime))
print(path.read_text())
# path.write_text("...")
# path.write_bytes()
Thu Feb 2 23:54:03 2023
print("Ecommerce initialized")
4、Working with Zip Files
from pathlib import Path
from zipfile import ZipFile
zip = ZipFile("files.zip", "w") # This statement will create this file in our current folder
for path in Path("ecommerce").rglob("*.*"): # All
zip.write(path)
zip.close()
But if something goes wrong here, a few statement might not be called
So we should either use a try finally block
Or the With statement which is shorter and clear
from pathlib import Path
from zipfile import ZipFile
with ZipFile("files.zip", "w") as zip: # This statement will create this file in our current folder
for path in Path("ecommerce").rglob("*.*"): # All
zip.write(path)
from pathlib import Path
from zipfile import ZipFile
# Because we only want to read from it, we're not going to open this in write mode!!!!
with ZipFile("files.zip") as zip:
print(zip.namelist())
['ecommerce/__init__.py', 'ecommerce/shopping/sales.py', 'ecommerce/shopping/__init__.py', 'ecommerce/shopping/__pycache__/sales.cpython-310.pyc', 'ecommerce/shopping/__pycache__/__init__.cpython-310.pyc', 'ecommerce/__pycache__/__init__.cpython-310.pyc', 'ecommerce/customer/__init__.py', 'ecommerce/customer/contact.py', 'ecommerce/customer/__pycache__/contact.cpython-310.pyc', 'ecommerce/customer/__pycache__/__init__.cpython-310.pyc']
from pathlib import Path
from zipfile import ZipFile
# Because we only want to read from it, we're not going to open this in write mode!!!!
with ZipFile("files.zip") as zip:
info = zip.getinfo("ecommerce/__init__.py")
print(info.file_size)
print(info.compress_size)
zip.extractall("extract") # Then we will have this extract directory with the content
30
30
5、Working with CSV Files
comma-separated-value
import csv
# file = open("data.csv", "w")
# file.close()
with open("data.csv", "w") as file:
writer = csv.writer(file)
writer.writerow(["transaction_id", "product_id", "price"])
writer.writerow([1000, 1, 5])
writer.writerow([1001, 2, 15])
import csv
with open("data.csv") as file:
reader = csv.reader(file)
print(list(reader))
for row in reader:
print(row)
只能得到:
[['transaction_id', 'product_id', 'price'], ['1000', '1', '5'], ['1001', '2', '15']]
Because this reader object has an index or a position that is initially set to the beginning of the file, after list(reader)
, that position goes to the end of the file. That is why we cannot iterate this reader twice
So
import csv
with open("data.csv") as file:
reader = csv.reader(file)
# print(list(reader))
for row in reader:
print(row)
['transaction_id', 'product_id', 'price']
['1000', '1', '5']
['1001', '2', '15']
6、Working with JSON Files
JSON (JavaScript Object Notation) is a lightweight data-interchange format. It is easy for humans to read and write.
import json
movies = [
{"id": 1, "title": "Terminator", "year": 1989},
{"id": 2, "title": "Kindergarten Cop", "year": 1989}
]
data = json.dumps(movies)
print(data)
[{"id": 1, "title": "Terminator", "year": 1989}, {"id": 2, "title": "Kindergarten Cop", "year": 1989}]
How to write data to Json File:
import json
from pathlib import Path
movies = [
{"id": 1, "title": "Terminator", "year": 1989},
{"id": 2, "title": "Kindergarten Cop", "year": 1989}
]
data = json.dumps(movies)
Path("movies.json").write_text(data) # "write_text" will create the movies.json file
How to read data from Json File:
import json
from pathlib import Path
data = Path("movies.json").read_text()
movies = json.loads(data)
print(movies)
print(movies[0])
print(movies[0]["title"])
[{'id': 1, 'title': 'Terminator', 'year': 1989}, {'id': 2, 'title': 'Kindergarten Cop', 'year': 1989}]
{'id': 1, 'title': 'Terminator', 'year': 1989}
Terminator
7、Working with a SQLite Database
SQLite is file-based. It is different from other SQL databases because unlike most other SQL databases, SQLite does not have a separate server process.
SQLite is a portable database resource. You have to get an extension of SQLite in whatever language you are programming in to access that database. You can access all of the desktop and mobile applications.
SQLite is a very lightweight database that we use for storing data of an application
It’s often the technology of choice for small applications like the apps that they run on phones and tablets
DB Browser for SQLite
创建后还要点写入更改!!
import sqlite3
import json
from pathlib import Path
movies = json.loads(Path("movies.json").read_text())
with sqlite3.connect("db.sqlite3") as conn: # "sqlite3.connect()" can create the conn for us
command = "INSERT INTO Movies VALUES(?, ?, ?)"
for movie in movies:
conn.execute(command, tuple(movie.values()))
conn.commit()
Then let me show you how to read data from this database
(We don’t need commit() now because we only need it when writing database)
import sqlite3
import json
from pathlib import Path
with sqlite3.connect("db.sqlite3") as conn:
command = "SELECT * FROM Movies"
cursor = conn.execute(command)
for row in cursor:
print(row)
(1, 'Terminator', 1989)
(2, 'Kindergarten Cop', 1989)
import sqlite3
import json
from pathlib import Path
with sqlite3.connect("db.sqlite3") as conn:
command = "SELECT * FROM Movies"
cursor = conn.execute(command)
for row in cursor:
print(row)
movies = cursor.fetchall()
print(movies)
If we run this, we’re not going to get any result because after iterate over this cursor, we’ll get to the end of the cursor, so we won’t be able to read it again
So:
import sqlite3
import json
from pathlib import Path
with sqlite3.connect("db.sqlite3") as conn:
command = "SELECT * FROM Movies"
cursor = conn.execute(command)
# for row in cursor:
# print(row)
movies = cursor.fetchall()
print(movies)
Then we get a list of tuples
[(1, 'Terminator', 1989), (2, 'Kindergarten Cop', 1989)]
8、Working with Timestamps
import time
def send_emails():
for i in range(10000):
pass
start = time.time()
send_emails()
end = time.time()
duration = end - start
print(duration)
0.00011014938354492188
9、Working with DateTimes
from datetime import datetime
import time
dt1 = datetime(2018, 1, 1)
dt2 = datetime.now()
dt3 = datetime.strptime("2018/01/01", "%Y/%m/%d")
dt4 = datetime.fromtimestamp(time.time())
print(dt1)
print(dt2)
print(dt3)
print(dt4)
print(f"{dt1.year}/{dt1.month}")
print(dt1.strftime("%Y/%m"))
print(dt2 > dt3)
2018-01-01 00:00:00
2023-02-11 16:06:54.815589
2018-01-01 00:00:00
2023-02-11 16:06:54.818239
2018/1
2018/01
True
10、Working with Time Deltas
from datetime import datetime, timedelta
dt1 = datetime(2018, 1, 1) + timedelta(days=1, seconds=1000)
print(dt1)
dt2 = datetime.now()
duration = dt2 - dt1
print(duration)
print("days", duration.days)
print("seconds", duration.seconds)
print("total_seconds", duration.total_seconds())
2018-01-02 00:16:40
1866 days, 15:54:59.237289
days 1866
seconds 57299
total_seconds 161279699.237289
11、Generating Random Values
import random
import string
print(random.random())
print(random.randint(1, 10))
print(random.choice([1, 2, 3, 4]))
print(random.choices([1, 2, 3, 4], k=2))
print("".join(random.choices("abcdefghi", k=4)))
print(",".join(random.choices("abcdefghi", k=4)))
print("".join(random.choices(string.ascii_letters + string.digits, k=4)))
numbers = [1, 2, 3, 4]
random.shuffle(numbers)
print(numbers)
0.726946092685319
6
1
[1, 4]
eihh
i,c,i,e
DGdI
[2, 4, 1, 3]
12、Opening the Browser
import webbrowser
print("Deployment completed")
webbrowser.open("http://google.com")
let me do it for u
13、Sending Emails
from email.mime.multipart import MIMEMultipart
from email.mime.text import MIMEText
from email.mime.image import MIMEImage
from pathlib import Path
import smtplib
message = MIMEMultipart
message["from"] = "Mosh Hamedani"
message["to"] = "testuser@codewithmosh.com"
message["subject"] = "This is a test"
message.attach(MIMEText("Body"))
message.attach(MIMEImage(Path("mosh.png").read_bytes()))
with smtplib.SMTP(host="smtp.gmail.come", port=587) as smtp:
smtp.ehlo()
smtp.starttls()
smtp.login("testuser@codewithmosh.com", "todayskyisblue1234")
print("Sent...")
14、Working with Templates
<!doctype html>
<html lang="en">
<head>
</head>
<body>
Hi <strong>$name</strong>, this is our test email.
</body>
</html>
from email.mime.multipart import MIMEMultipart
from email.mime.text import MIMEText
from email.mime.image import MIMEImage
from pathlib import Path
from string import Template
import smtplib
template = Template(Path("template.html").read_text())
message = MIMEMultipart
message["from"] = "Mosh Hamedani"
message["to"] = "testuser@codewithmosh.com"
message["subject"] = "This is a test"
body = template.substitute({"name": "John"})
message.attach(MIMEText(body, "html"))
message.attach(MIMEImage(Path("mosh.png").read_bytes()))
with smtplib.SMTP(host="smtp.gmail.come", port=587) as smtp:
smtp.ehlo()
smtp.starttls()
smtp.login("testuser@codewithmosh.com", "todayskyisblue1234")
print("Sent...")
15、Command-line Arguments
import sys
print(sys.argv)
The first item is always the name of our Python program
import sys
if len(sys.argv) == 1:
print("USAGE: python3 app.py <password>")
else:
password = sys.argv[1]
print("Password", password)
16、Running External Programs
import subprocess
completed = subprocess.run(["ls", "-l"])
print(type(completed))
print("args", completed.args)
print("returncode", completed.returncode)
print("stderr", completed.stderr)
print("stdout", completed.stdout)
total 56
drwxr-xr-x 2 fieldxia staff 64 Feb 2 23:33 __pycache__
-rw-r--r-- 1 fieldxia staff 54 Feb 10 03:40 data.csv
-rw-r--r-- 1 fieldxia staff 8192 Feb 11 02:57 db.sqlite3
drwxr-xr-x 6 fieldxia staff 192 Feb 2 23:54 ecommerce
drwxr-xr-x 3 fieldxia staff 96 Feb 10 03:33 extract
-rw-r--r-- 1 fieldxia staff 2859 Feb 9 18:27 files.zip
-rw-r--r-- 1 fieldxia staff 222 Feb 11 17:10 main.py
-rw-r--r-- 1 fieldxia staff 102 Feb 11 01:40 movies.json
-rw-r--r-- 1 fieldxia staff 125 Feb 11 16:57 template.html
drwxr-xr-x 6 fieldxia staff 192 Sep 9 15:58 venv
<class 'subprocess.CompletedProcess'>
args ['ls', '-l']
returncode 0
stderr None
stdout None
import subprocess
completed = subprocess.run(["python3", "other.py"],
capture_output=True,
text=True)
print("args", completed.args)
print("returncode", completed.returncode)
print("stderr", completed.stderr)
print("stdout", completed.stdout)
args ['python3', 'other.py']
returncode 0
stderr
stdout Here is a complicated script.
十、Python Package Index
1、Pypi
pypi.org
It’s a basically a repository of python packages built by people like you and I
2、Pip
如果是mac,要使用pip3
So this version is the version that came up with my python installation, but because pip is developed independently, upgraded from time to time, so right below that you can see the command that you need to run
So let me show you how to install an earlier version
下载后会自动unstall原先的版本
pip3 install requests==2.9.*
install the latest compatible version with version 2.9 so if there are patches
pip3 uninstall requests
pip3 install requests==2.*
import requests
response = requests.get("http://google.com")
print(response)
<Response [200]>
3、Virtual Environments
Let’s say we have another project I did that project you want to use an earlier version of this package with the current structure we cannot have two versions of any of these packages side by side, we can have only single version
To solve this problem, we need to create an isolated virtual environment for each application and installed this dependencies into that virtual isolated environment
Here in the project folder
python3 -m venv env 是一个命令行指令,用于在当前目录中创建一个新的 Python 虚拟环境,其中 “env” 是虚拟环境的名称(你也可以选择其他名称)。
虚拟环境是一个独立的 Python 运行时环境,它可以用来安装和管理项目所需的 Python 包和依赖项,而不会影响主机系统中的全局 Python 环境。这意味着你可以在同一台计算机上同时运行多个 Python 项目,并且每个项目都有自己的依赖项和包,而不会相互干扰。
在执行 python3 -m venv env 后,它将在当前目录中创建一个名为 env 的新目录,并在其中创建一个新的 Python 虚拟环境。你可以通过运行 source env/bin/activate(在 Linux/macOS)或 .\env\Scripts\activate(在 Windows)来激活虚拟环境。激活虚拟环境后,所有后续的 Python 包安装和脚本运行将在该虚拟环境中进行。
执行上述命令后,产生env目录
so now you’re in the virtual environment for this application
let’s go ahead and install an earlier version of requests package
which is different from the package that we installed globally on this machine, this is specific to this application
finally, when we’re done, we need to deactivate this virtual environment
4、Pipenv
Pipenv is a tool that provides all necessary means to create a virtual environment for your Python project.
It automatically manages project packages through the Pipfile file as you install or uninstall packages. Pipenv also generates the Pipfile.
然后删除上一节中的env目录,因为不再需要了
在当前项目目录下产生了:
但产生的虚拟环境不在这里,而是:
删除全局的requests:
Because we remove the request package from this list of global packages
And here Python doesn’t know where to locate this package, it has no knowledge of this new virtual environment
So we need to activate
how to deactivate:
5、Virtual Environments in VSCode
in a virtual environment
6、Pipfile
Pipfile.lock is a json file that lists the dependencies of our application
It tells us that no virtual environment has been created for this project yet
pipenv install
7、Managing the Dependencies
uninstall
8、Publishing Packages
(后来又用pipenv install了一次)
choosealicense
首先在moshpdf文件夹下新建__init__.py
,这样python就会将moshpdf看作一个package
然后
再在tests下新建setup.py
import setuptools
from pathlib import Path
setuptools.setup(
name="moshpdf",
version=1.0,
long_description=Path("README.md").read_text(),
packages=setuptools.find_packages(exclude=["tests", "data"])
)
然后有两个新目录,build和dist
然后上传
就可以在pypi网站搜到了
使用示例:
9、Docstrings
""" One line description.
A more detailed explanation.
"""
10、Pydoc