自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

再見(jiàn)pip & conda!管理Python依賴關(guān)系的更好的選擇:Poetry

開(kāi)發(fā) 開(kāi)發(fā)工具
雖然Poetry可能需要你的團(tuán)隊(duì)成員花費(fèi)一些額外的時(shí)間和精力來(lái)學(xué)習(xí)和適應(yīng),但從長(zhǎng)遠(yuǎn)來(lái)看,使用Poetry這樣的工具可以為你節(jié)省時(shí)間和精力。

在你的數(shù)據(jù)科學(xué)項(xiàng)目的開(kāi)始階段,使用pip或conda等依賴性管理工具可能就足夠了。

然而,隨著項(xiàng)目的擴(kuò)大,依賴關(guān)系的數(shù)量也在增加。這可能會(huì)使項(xiàng)目的環(huán)境難以重現(xiàn),并且在僅僅依靠pip或conda進(jìn)行依賴性管理時(shí)難以有效地維護(hù)它。

此時(shí) Poetry 應(yīng)運(yùn)而生,它是一個(gè)開(kāi)源庫(kù),提供了一個(gè)強(qiáng)大的工具來(lái)創(chuàng)建和維護(hù)具有一致環(huán)境的Python項(xiàng)目。在這篇文章中,我們將深入探討Poetry的優(yōu)勢(shì),并強(qiáng)調(diào)它與pip和conda的主要區(qū)別。

安裝的便利性

一鍵輕松安裝過(guò)程,能夠快速采用并將軟件包集成到我們的代碼庫(kù)中,從而節(jié)省時(shí)間和精力。

Conda

Conda的安裝格式對(duì)于不同的軟件包是不一致的。例如,要安裝polars,你需要運(yùn)行:

conda install -c conda-forge polar

而要安裝pandas,命令是:

conda install -c anaconda pandas

Pip

Pip對(duì)每個(gè)軟件包都有一致的安裝格式:

pip install package-name

Poetry

Poetry也都遵循相同的安裝格式:

poetry add package-name

可用的packages

軟件包選擇空間大,使得找到最適合需求的特定軟件包和版本更容易。

Conda

有些軟件包,如 "snscrape",不能通過(guò)conda安裝。此外,某些版本,如Pandas 2.0,可能無(wú)法通過(guò)Conda安裝。

雖然可以在conda的虛擬環(huán)境中使用pip來(lái)解決軟件包的限制,但conda不能跟蹤用pip安裝的依賴關(guān)系。

$ conda list
# packages in environment at /Users/khuyentran/miniconda3/envs/test-conda:
#
# Name                    Version                   Build  Channel

Pip

Pip可以安裝來(lái)自Python Package Index (PyPI)和其他存儲(chǔ)庫(kù)的任何軟件包。

Poetry

Poetry還可以安裝來(lái)自Python Package Index (PyPI)和其他存儲(chǔ)庫(kù)的軟件包。

依賴關(guān)系的數(shù)量

減少環(huán)境中的依賴性,可以簡(jiǎn)化開(kāi)發(fā)過(guò)程。

Conda

Conda提供完全的環(huán)境隔離,同時(shí)管理Python軟件包和系統(tǒng)級(jí)的依賴關(guān)系。與其他軟件包管理器相比,這可能會(huì)導(dǎo)致軟件包太大,在安裝和分發(fā)時(shí)可能會(huì)消耗更多的存儲(chǔ)空間。

$ conda install pandas

$ conda list          

# packages in environment at /Users/khuyentran/miniconda3/envs/test-conda:
#
# Name              Version         Build           Channel             
blas                1.0             openblas                          
bottleneck          1.3.5           py311ha0d4635_0                    
bzip2               1.0.8           h620ffc9_4                        
ca-certificates     2023.05.30      hca03da5_0                        
libcxx              14.0.6          h848a8c0_0                        
libffi              3.4.4           hca03da5_0                        
libgfortran         5.0.0           11_3_0_hca03da5_28                 
libgfortran5        11.3.0          h009349e_28                       
libopenblas         0.3.21          h269037a_0                        
llvm-openmp         14.0.6          hc6e5704_0                        
ncurses             6.4             h313beb8_0                        
numexpr             2.8.4           py311h6dc990b_1                    
numpy               1.24.3          py311hb57d4eb_0                    
numpy-base          1.24.3          py311h1d85a46_0                    
openssl             3.0.8           h1a28f6b_0                        
pandas              1.5.3           py311h6956b77_0                    
pip                 23.0.1          py311hca03da5_0                    
python              3.11.3          hb885b13_1                        
python-dateutil     2.8.2           pyhd3eb1b0_0                      
pytz                2022.7          py311hca03da5_0                    
readline            8.2             h1a28f6b_0                        
setuptools          67.8.0          py311hca03da5_0                    
six                 1.16.0          pyhd3eb1b0_1                      
sqlite              3.41.2          h80987f9_0                        
tk                  8.6.12          hb8d0fd4_0                        
tzdata              2023c           h04d1e81_0                        
wheel               0.38.4          py311hca03da5_0                    
xz                  5.4.2           h80987f9_0                        
zlib                1.2.13          h5a0b063_0

Pip

Pip只安裝軟件包所需的依賴性。

$ pip install pandas

$ pip list
Package         Version
--------------- -------
numpy           1.24.3
pandas          2.0.2
pip             22.3.1
python-dateutil 2.8.2
pytz            2023.3
setuptools      65.5.0
six             1.16.0
tzdata          2023.3

Poetry

Poetry也只安裝軟件包所需的依賴項(xiàng)。

$ poetry add pandas
$ poetry show

卸載Packages

卸載軟件包及其依賴關(guān)系可以釋放磁盤空間,防止不必要的雜亂,并優(yōu)化存儲(chǔ)資源的使用。

Pip

Pip只刪除指定的包,而不是它的依賴關(guān)系,可能會(huì)導(dǎo)致未使用的依賴關(guān)系長(zhǎng)期積累。這可能導(dǎo)致增加存儲(chǔ)空間的使用和潛在的沖突。

$ pip install pandas
$ pip uninstall pandas
$ pip list

Package         Version
--------------- -------
numpy           1.24.3
pip             22.0.4
python-dateutil 2.8.2
pytz            2023.3
setuptools      56.0.0
six             1.16.0
tzdata          2023.3

Conda

Conda刪除了該軟件包及其依賴關(guān)系。

$ conda install -c conda pandas

$ conda uninstall -c conda pandas

Collecting package metadata (repodata.json): done
Solving environment: done

## Package Plan ##

  environment location: /Users/khuyentran/miniconda3/envs/test-conda

  removed specs:
    - pandas


The following packages will be REMOVED:

  blas-1.0-openblas
  bottleneck-1.3.5-py311ha0d4635_0
  libcxx-14.0.6-h848a8c0_0
  libgfortran-5.0.0-11_3_0_hca03da5_28
  libgfortran5-11.3.0-h009349e_28
  libopenblas-0.3.21-h269037a_0
  llvm-openmp-14.0.6-hc6e5704_0
  numexpr-2.8.4-py311h6dc990b_1
  numpy-1.24.3-py311hb57d4eb_0
  numpy-base-1.24.3-py311h1d85a46_0
  pandas-1.5.3-py311h6956b77_0
  python-dateutil-2.8.2-pyhd3eb1b0_0
  pytz-2022.7-py311hca03da5_0
  six-1.16.0-pyhd3eb1b0_1


Proceed ([y]/n)? 

Preparing transaction: done
Verifying transaction: done
Executing transaction: done

Poetry

Poetry還刪除了該軟件包及其依賴關(guān)系。

$ poetry add pandas
$ poetry remove pandas

  ? Removing numpy (1.24.3)
  ? Removing pandas (2.0.2)
  ? Removing python-dateutil (2.8.2)
  ? Removing pytz (2023.3)
  ? Removing six (1.16.0)
  ? Removing tzdata (2023.3)

依賴性文件

依賴文件通過(guò)指定所需軟件包的確切版本或版本范圍來(lái)確保軟件項(xiàng)目環(huán)境的可重復(fù)性。

這有助于在不同的系統(tǒng)或不同的時(shí)間點(diǎn)上重新創(chuàng)建相同的環(huán)境,確保具有相同依賴關(guān)系的開(kāi)發(fā)人員之間的協(xié)作。

Conda

為了在Conda環(huán)境中保存依賴關(guān)系,需要手動(dòng)將它們寫(xiě)入一個(gè)文件中。在environment.yml文件中指定的版本范圍可能會(huì)導(dǎo)致不同的版本被安裝,在復(fù)制環(huán)境時(shí)可能會(huì)引入兼容性問(wèn)題。

我們假設(shè)已經(jīng)安裝了1.5.3版的pandas作為例子。下面是一個(gè)指定了依賴關(guān)系的environment.yml文件的例子:

# environment.yml
name: test-conda
channels:
  - defaults
dependencies:
  - python=3.8
  - pandas>=1.5

如果一個(gè)新的用戶試圖在pandas的最新版本是2.0的時(shí)候重現(xiàn)環(huán)境,那么pandas 2.0將被替代安裝。

# 創(chuàng)建并激活一個(gè)虛擬環(huán)境
$ conda env create -n env
$ conda activate env

# 列出當(dāng)前環(huán)境中的軟件包
$ conda list
...
pandas 2.0

如果代碼庫(kù)依賴于pandas 1.5.3版本特有的語(yǔ)法或行為,而語(yǔ)法在2.0版本中發(fā)生了變化,那么用pandas 2.0運(yùn)行代碼可能會(huì)帶來(lái)錯(cuò)誤。

Pip

同樣的問(wèn)題也可能發(fā)生在管道上。

# Requirements.txt
pandas>=1.5
# 創(chuàng)建并激活一個(gè)虛擬環(huán)境
$ python3 -m venv venv
$ source venv/bin/activate

# 安裝依賴項(xiàng)
$ pip install -r requirements.txt

# 列出軟件包
$ pip list
Package    Version
---------- -------
pandas       2.0
...
...

可以通過(guò)把它們凍結(jié)在requirements.txt文件中來(lái)確定版本:

```bash
$ pip freeze > requirements.txt
# requirements.txt

numpy==1.24.3
pandas==1.5.3
python-dateutil==2.8.2
pytz==2023.3
six==1.16.0
```

然而,這樣的代碼環(huán)境并不那么靈活,從長(zhǎng)遠(yuǎn)來(lái)看,可能更難維護(hù)。對(duì)依賴關(guān)系的任何改變都需要手動(dòng)修改requirements.txt文件,這可能很費(fèi)時(shí)且容易出錯(cuò)。

Poetry

Poetry在安裝軟件包時(shí)自動(dòng)更新pyproject.toml文件。

在下面的例子中,"pandas "包被加入了版本約束"^1.5"。這種靈活的版本管理方法確保你的項(xiàng)目可以適應(yīng)更新的版本,而不需要手動(dòng)調(diào)整。

$ poetry add 'pandas=^1.5'
# pyproject.toml

[tool.poetry.dependencies]
python = "^3.8"
pandas = "^1.5"

poetry.lock文件存儲(chǔ)了每個(gè)軟件包及其依賴關(guān)系的精確版本號(hào)。

# poetry.lock
...
[[package]]
name = "pandas"
version = "1.5.3"
description = "Powerful data structures for data analysis, time series, and statistics"
category = "main"
optional = false
python-versions = ">=3.8"

[package.dependencies]
numpy = [
    {version = ">=1.20.3", markers = "python_version < \"3.10\""},
    {version = ">=1.21.0", markers = "python_version >= \"3.10\""},
    {version = ">=1.23.2", markers = "python_version >= \"3.11\""},
]
python-dateutil = ">=2.8.2"
pytz = ">=2020.1"
tzdata = ">=2022.1"
...

這保證了所安裝軟件包的一致性,即使一個(gè)軟件包在 pyproject.toml 文件中指定了版本范圍。在這里,我們可以看到pandas 1.5.3被安裝,而不是pandas 2.0

$ poetry install

$ poetry show pandas

name         : pandas                                                                  
version      : 1.5.3                                                                   
description  : Powerful data structures for data analysis, time series, and statistics 

dependencies
 - numpy >=1.20.3
 - numpy >=1.21.0
 - numpy >=1.23.2
 - python-dateutil >=2.8.1
 - pytz >=2020.1

為開(kāi)發(fā)和生產(chǎn)環(huán)境提供單獨(dú)的依賴

通過(guò)分離依賴關(guān)系,可以明確區(qū)分開(kāi)發(fā)目的所需的包,如測(cè)試框架和代碼質(zhì)量工具,和生產(chǎn)環(huán)境所需的包,通常包括核心依賴關(guān)系。

這確保生產(chǎn)環(huán)境只包含運(yùn)行應(yīng)用程序所需的軟件包,減少?zèng)_突或兼容性問(wèn)題的風(fēng)險(xiǎn)。

Conda

Conda本質(zhì)上并不支持不同環(huán)境下的獨(dú)立依賴,但一個(gè)變通方法是創(chuàng)建兩個(gè)環(huán)境文件:一個(gè)用于開(kāi)發(fā)環(huán)境,一個(gè)用于生產(chǎn)環(huán)境。開(kāi)發(fā)文件包含了生產(chǎn)和開(kāi)發(fā)的依賴關(guān)系。

# environment.yml
name: test-conda
channels:
  - defaults
dependencies:
  # Production packages
  - numpy
  - pandas
# environment-dev.yml
name: test-conda-dev
channels:
  - defaults
dependencies:
  # Production packages
  - numpy
  - pandas
  # Development packages
  - pytest
  - pre-commit

Pip

Pip也不直接支持獨(dú)立的依賴關(guān)系,但類似的方法可以用獨(dú)立的需求文件。

# requirements.txt
numpy 
pandas
# requirements-dev.txt
-r requirements.txt
pytest
pre-commit
# Install prod
$ pip install -r requirements.txt

# Install both dev and prod
$ pip install -r requirements-dev.txt

Poetry

Poetry通過(guò)支持一個(gè)文件中的分組,簡(jiǎn)化了對(duì)依賴關(guān)系的管理。這使你能夠在一個(gè)地方跟蹤所有的依賴關(guān)系。

$ poetry add numpy pandas
$ poetry add --group dev pytest pre-commit
# pyproject.toml
[tool.poetry.dependencies]
python = "^3.8"
pandas = "^2.0"
numpy = "^1.24.3"

[tool.poetry.group.dev.dependencies]
pytest = "^7.3.2"
pre-commit = "^3.3.2"

要只安裝生產(chǎn)依賴性:

$ poetry install --only main

要同時(shí)安裝開(kāi)發(fā)和生產(chǎn)依賴:

$ poetry install

更新一個(gè)環(huán)境

更新依賴關(guān)系對(duì)于從較新的軟件包版本中引入的錯(cuò)誤修復(fù)、性能改進(jìn)和新功能中獲益至關(guān)重要。

Conda

Conda可以只更新一個(gè)指定的軟件包。

$ conda install -c conda pandas
$ conda install -c anaconda scikit-learn
# 新版本可用
$ conda update pandas
$ conda update scikit-learn

之后,需要手動(dòng)更新environment.yaml文件,使其與更新的依賴關(guān)系保持同步。

$ conda env export > environment.yml

Pip

Pip也只允許更新一個(gè)指定的軟件包,并要求我們手動(dòng)更新requirements.txt文件。

$ pip install -U pandas
$ pip freeze > requirements.txt

Poetry

使用Poetry,可以使用 update 命令來(lái)升級(jí) pyproject.toml 文件中指定的所有軟件包。這個(gè)動(dòng)作會(huì)自動(dòng)更新poetry.lock文件,確保軟件包規(guī)格和鎖文件的一致性。

$ poetry add pandas scikit-learn

# 新版本可用
poetry update

Updating dependencies
Resolving dependencies... (0.3s)

Writing lock file

Package operations: 0 installs, 2 updates, 0 removals

  ? Updating pandas (2.0.0 -> 2.0.2)
  ? Updating scikit-learn (1.2.0 -> 1.2.2)

依賴關(guān)系的解決

當(dāng)項(xiàng)目所需的包或庫(kù)有沖突的版本或不兼容的依賴性時(shí),就會(huì)發(fā)生依賴性沖突。正確解決沖突對(duì)于避免錯(cuò)誤、運(yùn)行時(shí)問(wèn)題或項(xiàng)目失敗至關(guān)重要。

Pip

pip是按順序安裝軟件包的,這意味著它按照指定的順序一個(gè)一個(gè)地安裝每個(gè)軟件包。當(dāng)軟件包有不兼容的依賴關(guān)系或版本要求時(shí),這種順序方法有時(shí)會(huì)導(dǎo)致沖突。

例如,假設(shè)你先安裝pandas==2.0.2,這需要numpy>=1.20.3。后來(lái),你用pip安裝numpy==1.20.2。盡管這將產(chǎn)生依賴性沖突,但pip會(huì)繼續(xù)更新numpy的版本。

$ pip install pandas==2.0.2

$ pip install numpy==1.22.2
Collecting numpy=1.20.2
  Attempting uninstall: numpy
    Found existing installation: numpy 1.24.3
    Uninstalling numpy-1.24.3:
      Successfully uninstalled numpy-1.24.3
ERROR: pip's dependency resolver does not currently take into account all the packages that are installed. This behaviour is the source of the following dependency conflicts.
pandas 2.0.2 requires numpy>=1.20.3; python_version < "3.10", but you have numpy 1.20.2 which is incompatible.
Successfully installed numpy-1.20.2

Conda

Conda使用一個(gè)SAT求解器來(lái)探索軟件包版本和依賴關(guān)系的所有組合,以找到一個(gè)兼容的集合。

例如,如果一個(gè)現(xiàn)有的軟件包對(duì)其依賴關(guān)系有特定的約束(例如,statsmodels==0.13.2要求numpy>=1.21.2,<2.0a0),而你要安裝的軟件包不符合該要求(例如,numpy<1.21.2),conda不會(huì)立即引發(fā)錯(cuò)誤。相反,它將勤奮地搜索所有需要的軟件包及其依賴的兼容版本,只有在沒(méi)有找到合適的解決方案時(shí)才會(huì)報(bào)告錯(cuò)誤。

$ conda install 'statsmodels==0.13.2'

$ conda search 'statsmodels==0.13.2' --info
dependencies: 
  - numpy >=1.21.2,<2.0a0
  - packaging >=21.3
  - pandas >=1.0
  - patsy >=0.5.2
  - python >=3.9,<3.10.0a0
  - scipy >=1.3

$ conda install 'numpy<1.21.2'

...
Package ca-certificates conflicts for:
python=3.8 -> openssl[version='>=1.1.1t,<1.1.2a'] -> ca-certificates
openssl -> ca-certificates
ca-certificates
cryptography -> openssl[version='>1.1.0,<3.1.0'] -> ca-certificates

Package idna conflicts for:
requests -> urllib3[version='>=1.21.1,<1.27'] -> idna[version='>=2.0.0']
requests -> idna[version='>=2.5,<3|>=2.5,<4']
idna
pooch -> requests -> idna[version='>=2.5,<3|>=2.5,<4']
urllib3 -> idna[version='>=2.0.0']

Package numexpr conflicts for:
statsmodels==0.13.2 -> pandas[version='>=1.0'] -> numexpr[version='>=2.7.0|>=2.7.1|>=2.7.3']
numexpr
pandas==1.5.3 -> numexpr[version='>=2.7.3']

Package patsy conflicts for:
statsmodels==0.13.2 -> patsy[version='>=0.5.2']
patsy

Package chardet conflicts for:
requests -> chardet[version='>=3.0.2,<4|>=3.0.2,<5']
pooch -> requests -> chardet[version='>=3.0.2,<4|>=3.0.2,<5']

Package python-dateutil conflicts for:
statsmodels==0.13.2 -> pandas[version='>=1.0'] -> python-dateutil[version='>=2.7.3|>=2.8.1']
python-dateutil
pandas==1.5.3 -> python-dateutil[version='>=2.8.1']

Package setuptools conflicts for:
numexpr -> setuptools
pip -> setuptools
wheel -> setuptools
setuptools
python=3.8 -> pip -> setuptools
pandas==1.5.3 -> numexpr[version='>=2.7.3'] -> setuptools

Package brotlipy conflicts for:
urllib3 -> brotlipy[version='>=0.6.0']
brotlipy
requests -> urllib3[version='>=1.21.1,<1.27'] -> brotlipy[version='>=0.6.0']

Package pytz conflicts for:
pytz
pandas==1.5.3 -> pytz[version='>=2020.1']
statsmodels==0.13.2 -> pandas[version='>=1.0'] -> pytz[version='>=2017.3|>=2020.1']

雖然這種方法提高了找到解決方案的機(jī)會(huì),但它可能是計(jì)算密集型的,特別是在處理繁雜的環(huán)境時(shí)。

Poetry

通過(guò)關(guān)注項(xiàng)目的直接依賴關(guān)系,Poetry的確定性解析器縮小了搜索空間,使解析過(guò)程更加高效。它評(píng)估指定的約束條件,如版本范圍或特定版本,并立即識(shí)別任何沖突。

$ poetry add 'seaborn==0.12.2'
$ poetry add 'matplotlib<3.1' 

Because poetry shell depends on seaborn (0.12.2) which depends on matplotlib (>=3.1,<3.6.1 || >3.6.1), matplotlib is required.
So, because poetry shell depends on matplotlib (<3.1), version solving failed.

這種即時(shí)反饋有助于防止?jié)撛诘膯?wèn)題升級(jí),并允許開(kāi)發(fā)人員在開(kāi)發(fā)過(guò)程中及早解決問(wèn)題。例如,在下面的代碼中,我們可以放寬對(duì)seaborn的要求,以便能夠安裝特定版本的matplotlib:

poetry add 'seaborn<=0.12.2'  'matplotlib<3.1' 

Package operations: 1 install, 2 updates, 4 removals

  ? Removing contourpy (1.0.7)
  ? Removing fonttools (4.40.0)
  ? Removing packaging (23.1)
  ? Removing pillow (9.5.0)
  ? Updating matplotlib (3.7.1 -> 3.0.3)
  ? Installing scipy (1.9.3)
  ? Updating seaborn (0.12.2 -> 0.11.2)

總結(jié)

綜上所述,Poetry提供了比pip和conda更多的優(yōu)勢(shì):

  1. 一致的軟件包安裝:Poetry提供了一個(gè)一致的格式來(lái)安裝任何軟件包,確保整個(gè)項(xiàng)目有一個(gè)標(biāo)準(zhǔn)化的方法。
  2. 廣泛的軟件包選擇:Poetry提供了對(duì)PyPI上廣泛的軟件包的訪問(wèn),使你可以為你的項(xiàng)目利用一個(gè)多樣化的生態(tài)系統(tǒng)。
  3. 高效的依賴性管理:Poetry只為指定的軟件包安裝必要的依賴性,減少你環(huán)境中不相干的軟件包的數(shù)量。
  4. 簡(jiǎn)化的軟件包移除:Poetry簡(jiǎn)化了軟件包及其相關(guān)依賴關(guān)系的移除,使其易于維護(hù)一個(gè)干凈和高效的項(xiàng)目環(huán)境。
  5. 依賴性解決:Poetry的確定性解析器有效地解決了依賴關(guān)系,及時(shí)識(shí)別并處理任何不一致或沖突。

雖然Poetry可能需要你的團(tuán)隊(duì)成員花費(fèi)一些額外的時(shí)間和精力來(lái)學(xué)習(xí)和適應(yīng),但從長(zhǎng)遠(yuǎn)來(lái)看,使用Poetry這樣的工具可以為你節(jié)省時(shí)間和精力。

責(zé)任編輯:武曉燕 來(lái)源: 數(shù)據(jù)STUDIO
相關(guān)推薦

2024-01-30 09:08:07

PoetryPython包管理工具

2024-03-05 10:45:07

PoetryPython開(kāi)發(fā)

2019-09-23 11:07:00

PythonRedis軟件

2021-03-14 13:00:36

FedoraPoetry Python

2024-04-15 07:00:00

Python開(kāi)發(fā)Hatch

2022-07-01 09:17:14

Pythonpoetry工具

2021-08-13 08:42:48

Python 編程技巧poetry

2022-08-05 13:03:09

Python依賴管理代碼

2023-12-15 14:26:00

版本管理工具

2024-02-20 13:08:00

2018-11-19 10:30:39

du命令Linux

2010-07-08 15:28:39

UML類圖依賴關(guān)系

2011-04-29 10:32:46

項(xiàng)目管理

2019-09-18 13:50:34

CondaMacOSAnsible

2021-12-22 10:25:13

locateLinuxplocate

2022-02-07 08:58:54

DCIM數(shù)據(jù)中心

2016-12-02 17:14:46

2021-12-21 06:37:32

CIOCMO首席信息官

2015-10-10 14:28:36

漏洞管理漏洞管理工具

2010-07-09 10:36:14

UML類圖關(guān)系
點(diǎn)贊
收藏

51CTO技術(shù)棧公眾號(hào)