Bu sorunun birkaç kez sorulmasına ve yanıtlanmasına rağmen (örneğin, burada , burada , burada ve burada ) bence hiçbir mevcut cevap, yanıtın tüm sonuçlarını tam veya kısaca yakalayamaz.-m bayrağın . Bu nedenle, aşağıdakiler daha önce olanları geliştirmeye çalışacaktır.
Giriş (TLDR)
-mKomut hepsi değil bir çok şey mutlaka her zaman ihtiyaç olacaktır yapar. Kısacası o: piton komut eklemek için bir dizin seçmek için bir modulename ziyade dosya (2) üzerinden yürütülecek verir edilecek için (1) verir sys.pathiçinimport çözünürlük ve (3) göreli ithalat ile piton komut komut satırından çalıştırılmasına izin verir .
Hazırlıklar
Açıklamak -mBayrağı önce küçük bir terminoloji ortaya koymalıyız.
İlk olarak, Python'un birincil organizasyon birimi bir modül olarak bilinir . Modüllerin iki çeşidi vardır: kod modülleri ve paket modülleri. Kod modülü, python yürütülebilir kodu içeren herhangi bir dosyadır. Paket modülü, diğer modülleri (kod modülleri veya paket modülleri) içeren bir dizindir. En yaygın kod modülleri *.pydosyalardır, en yaygın paket modülleri ise__init__.py dosya .
İkincisi, tüm modüller iki farklı şekilde benzersiz bir şekilde tanımlanabilir: <modulename>ve <filename>. Modüller çoğunlukla Python kodundaki modulename (örn. import <modulename>) Ve komut satırındaki dosya adıyla (örn. ) Tanımlanır python <filename>. Tüm Python yorumlayıcıları, iyi tanımlanmış bir dizi kural aracılığıyla modül adlarını dosya adlarına dönüştürebilir. Bu kurallar sys.pathdeğişkene bağlıdır ve bu nedenle eşleme bu değer değiştirilerek değiştirilebilir (bunun nasıl yapılacağı hakkında daha fazla bilgi için bkz. PEP 302 ).
Üçüncü olarak, tüm modüller (hem kod hem de paket) yürütülebilir (modülle ilişkili kodun Python yorumlayıcısı tarafından değerlendirileceği anlamına gelir). Yürütme yöntemine ve modül türüne bağlı olarak, hangi kod değerlendirilir ve ne zaman biraz değişebilir. Örneğin, biri bir paket modülünü yürütürse, python <filename>o <filename>/__init__.pyzaman değerlendirilir <filename>/__main__.py. Öte yandan, eğer aynı paket modülünü yürütürse, import <modulename>sadece paketler __init__.pyyürütülür.
Tarihsel Gelişimi -m
-M bayrağı ilk olarak Python 2.4.1'de tanıtıldı . Başlangıçta tek amacı, yürütülecek bir python modülünü tanımlamak için alternatif bir yol sağlamaktı. İkimiz de bilse olduğunu, <filename>ve <modulename>bir modül için aşağıdaki iki komut eşdeğerdir: python <filename> <args>ve python -m <modulename> <args>. Ek olarak, PEP 338'e göre, bu yineleme -msadece üst düzey modül adları ile çalışmıştır (yani, herhangi bir müdahale paketi olmadan doğrudan sys.path üzerinde bulunabilen modüller).
Tamamlanmasıyla birlikte PEP 338-m işlevselliği desteği için uzatıldı <modulename>üst düzey modulenames ötesinde temsiller. Bu http.server, artık tam olarak desteklenen gibi adlar anlamına geliyordu . Bu geliştirme ayrıca bir modüldeki tüm paketlerin __init__.pymodülün kendisiyle birlikte yüklendiği (yani tüm paket dosyalarının değerlendirildiği) anlamına geliyordu .
Son büyük özellik geliştirmesi PEP 366-m ile geldi . Bu güncellemeyle sadece mutlak ithalatı değil, aynı zamanda açık göreli ithalatı da destekleme yeteneği kazanıldı. Bu, komuttaki adlandırılmış modül için değişken değiştirilerek başarıldı .-m__package__-m
Kullanım Örnekleri
-M bayrağı için iki önemli kullanım durumu vardır:
Dosya adlarını bilmeyen komut satırından modülleri yürütmek için. Bu kullanım durumu, Python yorumlayıcısının modül adlarını dosya adlarına nasıl dönüştüreceğini bilmesi gerçeğinden yararlanır. Bu, özellikle komut satırından stdlib modüllerini veya 3. taraf modülünü çalıştırmak istediğinde avantajlıdır. Örneğin, çok az kişi http.servermodülün dosya adını bilir, ancak çoğu kişi modül adını bilir, böylece komut satırını kullanarak komut satırını yürütebiliriz python -m http.server.
Yüklemeye gerek kalmadan mutlak ithalat içeren bir yerel paket yürütmek. Bu kullanım durumu PEP 338'de ayrıntılı olarak açıklanmaktadır ve geçerli çalışma dizininin sys.pathmodül dizini yerine eklenmesi gerçeğinden yararlanmaktadır . Bu kullanım durumu, pip install -e .bir paketi geliştirme / düzenleme modunda yüklemek için kullanılmaya çok benzer .
eksiklikleri
-mYıllar boyunca yapılan tüm geliştirmelerle birlikte hala büyük bir eksikliği var - sadece python ile yazılmış kod modüllerini yürütebilir (yani, * .py). Örneğin, -mC derlenmiş kod modülünü yürütmek için kullanılırsa, aşağıdaki hata üretilir No code object available for <modulename>( daha fazla ayrıntı için buraya bakın).
Detaylı Karşılaştırmalar
Python komutu ile modül yürütmenin etkileri (örn. python <filename>):
sys.path içindeki son dizini içerecek şekilde değiştirildi <filename>
__name__ ayarlandı '__main__'
__package__ ayarlandı None
__init__.py herhangi bir paket için değerlendirilmez (paket modülleri için kendi paketi dahil)
__main__.pypaket modülleri için değerlendirilir; kod, kod modülleri için değerlendirilir.
Modül yürütmenin import deyimi (yani import <modulename>) ile etkileri :
sys.patholduğu değil herhangi bir şekilde modifiye
__name__ mutlak biçimine ayarlanır <modulename>
__package__ içindeki üst paket olarak ayarlandı <modulename>
__init__.py tüm paketler için değerlendirilir (paket modülleri için kendi paketleri dahil)
__main__.pyolduğu değil paket modülleri için değerlendirilir; kod, kod modülleri için değerlendirilir
-M bayrağı (örn. python -m <modulename>) İle modül yürütülmesinin etkileri :
sys.path geçerli dizini içerecek şekilde değiştirildi
__name__ ayarlandı '__main__'
__package__ içindeki üst paket olarak ayarlandı <modulename>
__init__.py tüm paketler için değerlendirilir (paket modülleri için kendi paketleri dahil)
__main__.pypaket modülleri için değerlendirilir; kod, kod modülleri için değerlendirilir
Sonuç
-mBayrak en basit, modulenames yerine dosya adlarını kullanarak komut satırından piton komut dosyalarını yürütmek için bir araç olarak vardır. Ek olarak, ifadelerin -mgücünü import(örneğin, açık göreli ithalat ve otomatik paket __init__değerlendirmesi için destek ) python komut satırının rahatlığıyla birleştiren ek işlevler sağlar .
-marama yapıyor gibi görünüyormymod1. Örnek:python -m SimpleHTTPServerçalışır,python SimpleHTTPServerbaşarısız olurcan't open file 'SimpleHTTPServer': [Errno 2] No such file or directory.