क्या फ़ाइल नाम में स्थान की अनुमति नहीं है?


31

यह कहा जाता है कि सामान्य रूप से यूनिक्स और लिनक्स पर, आपको फ़ाइल (साधारण फ़ाइल, डीआईआर, लिंक, डिवाइस फ़ाइल, ...) के फ़ाइल नाम में रिक्त स्थान होने से बचना चाहिए।

लेकिन मैं हर समय ऐसा करता हूं। एक स्थान के साथ एक फ़ाइल नाम के लिए,

  • नॉटिलस में, अंतरिक्ष चरित्र को अंतरिक्ष के रूप में दिखाया गया है।
  • बैश टर्मिनल में, मैं या तो \ एक स्थान का प्रतिनिधित्व करने के लिए उपयोग करता हूं , या दोहरे उद्धरणों की एक जोड़ी के भीतर फ़ाइल नाम को संलग्न करता हूं ।
  • कुछ अनुप्रयोगों की फाइलों में (Nautilus, सुनिश्चित नहीं है कि अगर OS ​​भी ऐसा करेगा), फ़ाइल नाम के स्थान के साथ लिखा गया है %20

क्या वास्तव में एक फ़ाइल नाम में एक जगह की अनुमति नहीं है?

आप फ़ाइल नाम में स्थान के साथ सही तरीके से कैसे उपयोग या व्यवहार करते हैं?


17
इसकी अनुमति है लेकिन यह वास्तव में, वास्तव में कष्टप्रद है। इसका कोई कारण नहीं है। यह मत करो।
मोनिका

3
आप एक फाइल भी बना सकते हैं जिसका नाम -rf ~(उपयोग touch -- "-rf ~") है, लेकिन मैं इसकी सिफारिश नहीं करूंगा।
इयान डी। स्कॉट

5
आप इसे कर सकते हैं, इसकी अनुमति है, जैसे "सीडी" नामक एक आत्म-विनाशकारी स्क्रिप्ट बनाना लेकिन आपको ऐसा नहीं करना चाहिए। आपकी फ़ाइल पहले से ही 3 अलग-अलग टूलों में अलग दिखती है, क्या यह बहुत बुरा नहीं है?
फाल्को

7
हर कोई राय साझा नहीं करता है कि यह वास्तव में है, वास्तव में कष्टप्रद है। और "इसका कोई कारण नहीं है" इतना स्पष्ट रूप से गलत है कि इसे अस्वीकार करने की आवश्यकता नहीं है। मैंने वर्षों पहले ठीक से रिक्त स्थान को संभालना और सीखा है, और अधिकांश भाग के लिए यह वास्तव में एक बड़ी बात नहीं है।

2
@snailboat स्पेस वास्तविक समस्या का एक लक्षण है जो मानकीकरण की कमी है। यूनिक्स फाइलसिस्टम लगभग अप्रतिबंधित बाइनरी ब्लॉब के लिए फ़ाइल "नाम" की अनुमति देते हैं। केवल अवैध बाइट्स 0 और 47 ( /विभाजक) हैं। सभी 254 बचे हुए बाइट्स का उपयोग करने से अकथनीय एल्ड्रिच "नामों" के सभी शिष्टाचार के द्वार खुल जाते हैं। स्पष्ट रूप से यह पागल है, लेकिन हर कोई इस बात पर सहमत नहीं है कि "समझदार" क्या है, और विभिन्न वर्ण अलग-अलग टूल को तोड़ देंगे। सभी की पवित्रता का प्रतिच्छेदन काफी छोटा है
jw013

जवाबों:


48

रिक्त स्थान, और वास्तव में /NUL और NUL को छोड़कर हर चरित्र की अनुमति है। फ़ाइल नाम में रिक्त स्थान का उपयोग नहीं करने की सिफारिश इस खतरे से आती है कि उन्हें सॉफ़्टवेयर द्वारा गलत तरीके से समझा जा सकता है जो खराब समर्थन करता है। यकीनन, इस तरह के सॉफ्टवेयर छोटी गाड़ी है। लेकिन यकीनन, शेल स्क्रिप्टिंग जैसी प्रोग्रामिंग लैंग्वेज सॉफ्टवेयर को लिखना भी बहुत आसान बना देती है, जब इसमें स्पेस के साथ फाइलनाम के साथ प्रस्तुत किया जाता है, और इन बग्स के माध्यम से फिसलने की प्रवृत्ति होती है क्योंकि शेल स्क्रिप्ट अक्सर अपने डेवलपर्स द्वारा स्पेस के साथ फाइलनाम का उपयोग करके परीक्षण नहीं किया जाता है। उन्हें।

फिल्नाम में %20अक्सर जगह नहीं देखी जाती है। यह ज्यादातर (वेब) URL के लिए उपयोग किया जाता है। हालाँकि यह सच है कि URL से%-कोडिंग कभी-कभी दुर्घटना के कारण फ़ाइल नाम में बदल जाती है।


6
यह "URL एन्कोडिंग" या "प्रतिशत एन्कोडिंग" en.wikipedia.org/wiki/URL_encoding प्रति है कि सबसे अधिक उपयुक्त नाम शायद "URI एन्कोडिंग" है, लेकिन लोगों को लगता है यूआरएल तुलना में आसान कहने के लिए यूआरआई , तो यह की एक आम रूप है मिथ्या नाम। ध्यान दें कि URI के आरक्षित वर्णों का सेट इससे बड़ा है, जो * nix filenames के लिए है।
गोल्डीलॉक्स

1
@ मुझे नहीं पता कि आप किसी भी कमांड लाइन तर्क में NUL वर्ण निर्दिष्ट कर सकते हैं bash। मैंने कुछ चीजों की कोशिश की जैसे कि इसे Ctrl-V के साथ उद्धृत करना और कुछ ऐसा, $(echo -e \\0)लेकिन यह काम नहीं किया। बात यह है कि, एनयूएल को फाइलनाम में उपयोग नहीं किया जा सकता है, इसका उपयोग सी स्ट्रिंग्स में नहीं किया जा सकता है (क्योंकि यह स्ट्रिंग टर्मिनेटर है) और सभी अंतर्निहित एपीआई के साथ-साथ सी प्रोग्राम द्वारा संकलित लगभग सभी स्ट्रिंग उस प्रारूप का उपयोग करते हैं। । चूंकि bashसी में लिखा गया है, इसलिए इसमें एनयूएल के साथ किसी भी तार के लिए बस कोई समर्थन नहीं हो सकता है। मैं गलत हो सकता है, कुछ अस्पष्ट तरीका हो सकता है ...
सेलाडा

1
संदर्भ पर निर्भर करता है। स्ट्रिंग फ़ंक्शंस आम तौर पर अंतिम नल की गिनती नहीं करते हैं (या बल्कि, पहला नल स्ट्रिंग का अंत है, भले ही इसके बाद सामान हो), इसलिए उस अर्थ में इसकी लंबाई शून्य है और इसलिए इसे खाली माना जाएगा।
गोल्डीलॉक्स

3
@ बेशक आप उपयोग कर सकते हैं NULऔर बैश कर सकते हैं , आपको जरूरत है $'\0'। उदाहरण के लिए:find . -print0 | while read -d $'\0' f; do echo "$f"; done
terdon

1
@goldilocks क्या लोग वास्तव में 'url' के रूप में URL का उच्चारण करते हैं, मोटे तौर पर 'कर्ण' के साथ तुकबंदी?
माइल्स रुट

17

फ़ाइलनामों में रिक्त स्थान की अनुमति है, जैसा कि आपने देखा है।

यदि आप विकिपीडिया में इस चार्ट में "सबसे अधिक UNIX फाइल सिस्टम" प्रविष्टि देखते हैं, तो आप ध्यान देंगे:

  • किसी भी 8-बिट वर्ण सेट की अनुमति है। हम इस छतरी के नीचे भी 7-बिट ASCII की सदस्यता ले सकते हैं, क्योंकि यह विभिन्न 8-बिट सेटों का सबसेट है और इसे हमेशा 8 बिट बाइट्स का उपयोग करके लागू किया जाता है।

  • केवल निषिद्ध वर्ण हैं /और "अशक्त" हैं। "नल" एक शून्य बाइट को संदर्भित करता है, लेकिन इन्हें पाठ डेटा में वैसे भी अनुमति नहीं है।

हालाँकि , यदि आप शेल का कोई उपयोग करते हैं, तो आप महसूस कर सकते हैं कि कुछ अक्षर हैं जो परेशानी पैदा करेंगे, सबसे महत्वपूर्ण *, जो कि एक POSIX ग्लोबबिंग ऑपरेटर है।

इस बात पर निर्भर करते हुए कि आप "परेशानी" को कैसे परिभाषित करना चाहते हैं, आप उसमें व्हाट्सएप (स्पेस, टैब, न्यूलाइन्स इत्यादि) को शामिल कर सकते हैं, क्योंकि इससे उद्धरण की आवश्यकता पैदा होती है ""। लेकिन यह अपरिहार्य है, चूंकि रिक्त स्थान की अनुमति है, इसलिए ...

आप फ़ाइल नाम में स्थान के साथ सही तरीके से कैसे उपयोग या व्यवहार करते हैं?

शेल / कमांड लाइन के संदर्भ में, फ़ाइल नाम को एकल या दोहरे उद्धरण में लपेटें (लेकिन ध्यान दें कि वे एक ही WRT अन्य मुद्दे नहीं हैं), या रिक्त स्थान से बाहर निकलें \, जैसे:

> foo my\ file\ with\ spaces\ in\ the\ name

1
आप बैश में एनयूएल चरित्र कैसे निर्दिष्ट करते हैं? मैं इसे एक फ़ाइलनाम में परीक्षण करना चाहता हूं।
टिम

1
आप नहीं कर सकते। "निष्पादित शब्दार्थ" इस तथ्य को संदर्भित करता है कि सी में (और हर दूसरी भाषा जो मुझे पता है), पाठ स्ट्रिंग्स अशक्त हैं। शेल सी में कार्यान्वित किया गया है। जिस चुपके से मैं सोच सकता था वह है touch $(echo -e "foo\00bar")- एक अष्टाधारी मूल्य के रूप में -eप्रक्रियाएं \0N, लेकिन यह अभी भी कहीं खो जाता है, जैसा कि बस नाम की एक फ़ाइल बनाता है foobar। बेशक NULL प्रिंट करने योग्य नहीं है, लेकिन मैं गारंटी देता हूं कि यह C स्ट्रिंग प्रतिबंध के कारण वहां से चला गया है।
गोल्डीलॉक्स

"टेक्स्ट स्ट्रिंग्स को शून्य समाप्त कर दिया गया है" -> आगे समझाने के लिए: स्ट्रिंग्स को हमेशा एक शून्य बाइट के साथ अंत में संग्रहीत किया जाता है, यही कारण है कि यह पाठ में "अनुमति नहीं है": यदि आप एक सम्मिलित करते हैं, तो आपने स्ट्रिंग को प्रभावी रूप से समाप्त कर दिया है उस बिंदु पर। जैसे।, अधिकांश इरादों और उद्देश्यों के लिए foo[NULL]barसमाप्त हो जाएगा foo। तथ्य यह है कि echo -eNULL के साथ ऐसा नहीं होता है कहीं न कहीं से बाहर निकाल दिया गया है।
गोल्डीलॉक्स

5
प्रोग्रामिंग भाषाओं का एक बड़ा हिस्सा तार में अशक्त पात्रों की अनुमति देता है। यह सिर्फ ऐसा होता है कि मुख्य भाषा जो सी नहीं है, जो यूनिक्स पर बनी है - और अधिकांश यूनिक्स गोले या तो तार में अशक्त वर्णों की अनुमति नहीं देते हैं। किसी भी स्थिति में, @Tim, सभी यूनिक्स इंटरफेस अशक्त-समाप्त स्ट्रिंग्स का उपयोग करते हैं, इसलिए एक अशक्त बाइट एक ऐसी चीज है जिसे आप कभी भी एक फ़ाइल नाम में नहीं रख सकते हैं (प्लस /जो निर्देशिका विभाजक है और उद्धृत नहीं किया जा सकता है, इसलिए पथनाम में हो सकता है लेकिन एक फ़ाइल नाम में नहीं)।
गिल्स एसओ-

1
... लेकिन [फिर से कोई बात नहीं]। कुछ ऐसा नहीं है जो मैं बहुत बार करूँगा, वैसे भी। मेरे मन में उनके लिए पाठीय डेटा में होने का कोई कारण नहीं है। मैंने इसे ठीक कर दिया होगा, लेकिन यह एक टिप्पणी है।
गोल्डीलॉक्स

3

इसका कारण काफी हद तक ऐतिहासिक है - समय के रिक्त स्थान की WAY को फाइलनामों में अनुमति नहीं दी गई थी, इसलिए रिक्त स्थान का उपयोग कीवर्ड / फ़ाइलनाम विभाजक के रूप में किया गया था। भविष्य के खोल दुभाषियों को पुरानी लिपियों के साथ रिवर्स-संगत होना पड़ता था, और इस प्रकार हम आज के सिरदर्द के साथ फंस गए हैं।

प्रक्रियाओं के डेवलपर्स जिन्हें मनुष्यों के साथ बहुत अधिक निपटने की आवश्यकता नहीं है, वे पूरी तरह से रिक्त स्थान को गिराकर चीजों को बहुत आसान बना सकते हैं। Apple ऐसा करता है, / System / Library / CoreServices / की सामग्री में बहुत कम स्थान हैं, रिक्त स्थान वाले प्रोग्राम उपयोगकर्ता की ओर से खोले जाते हैं, और WouldLookStrangeIfCamelCased। ऐसे ही यूनिक्स-ओनली पाथ भी स्पेस से बचते हैं।

(कुछ हद तक संबंधित किस्सा: 90 के दशक के मध्य में एक विंडोज ड्रोन ने कहा "एक चीज का नाम आप एक मैक पर कर सकते हैं जो मैं विंडोज पर नहीं कर सकता" -> "फ़ाइल नाम में 12 वर्णों का उपयोग करें।" -> साइलेंस। उन 12 अक्षरों में भी संभव है)


1
मैं वी 6 यूनिक्स (सी। 1978) का उपयोग करता था। रिक्त स्थान की अनुमति दी गई थी। एक कार्य मुझे फ़ाइल सिस्टम को पार्स करने के लिए एक प्रोग्राम लिखने (डायरेक्ट डिस्क आई / ओ का उपयोग करके) लिखने का था और एक फ़ाइल की तलाश थी जिसके नाम में रिक्त स्थान और बैकस्पेस थे।
w Augk

क्या वे रिक्त स्थान पूरी तरह से छोड़ देते हैं - या फ़ाइल नाम में बहुत कम स्थान हैं?
mikeserv

2

तो हाँ, जैसा कि कई बार कहा गया है, एक फ़ाइलनाम में लगभग कोई भी चरित्र हो सकता है। लेकिन यह कहा जा सकता है कि एक की जरूरत है फ़ाइल नाम है नहीं एक फ़ाइल। यह एक फ़ाइल के रूप में कुछ वजन ले करता है विशेषता में है कि आप आम तौर पर करने के लिए एक फ़ाइल नाम की जरूरत है खोलने के एक फ़ाइल है, लेकिन एक फ़ाइल के नाम केवल अंक वास्तविक फ़ाइल को। यह एक लिंक है, जिसे उस निर्देशिका में संग्रहीत किया गया है, जो इनकोड संख्या के साथ दर्ज की गई है - जो एक वास्तविक फ़ाइल के लिए एक बहुत करीब सन्निकटन है ।

तो, आप जानते हैं, जो आप चाहते हैं उसे कॉल करें। कर्नेल परवाह नहीं करता है - सभी फ़ाइल संदर्भ इसे संभाल लेंगे वैसे भी वास्तविक इनोड संख्या से निपटेंगे। फ़ाइलनाम मानव उपभोग के लिए एक चीज है - यदि आप इसे एक पागल चीज बनाना चाहते हैं, तो ठीक है, यह आपकी फाइलसिस्टम है। यहाँ, मैं कुछ पागल सामान करूँगा:

पहले मैं 20 फाइलें बनाऊंगा, और उन्हें रिक्त स्थान के अलावा कुछ भी नाम नहीं दूंगा, प्रत्येक फ़ाइलनाम में अंतिम से अधिक स्थान होगा:

until [ $((i=$i+1)) -gt 20 ]
do  v=$v' ' && touch ./"$v"
done

यह थोड़े मजाकिया है। मेरी ओर देखो ls:

ls -d ./*
./      ./          ./              ./                  ./                 
./      ./          ./              ./                  ./                  
./      ./          ./              ./                  ./                   
./      ./          ./              ./                  ./     

अब मैं इस निर्देशिका को प्रतिबिंबित करने जा रहा हूं:

set -- * ; mkdir ../mirror
ls -i1qdU -- "$@" |
sh -c 'while read inum na
    do  ln -T "$1" ../mirror/$inum
    shift ; done' -- "$@"
ls -d ../mirror/*

यहाँ ../mirror/सामग्री है:

../mirror/423759  ../mirror/423764  ../mirror/423769  ../mirror/423774
../mirror/423760  ../mirror/423765  ../mirror/423770  ../mirror/423775
../mirror/423761  ../mirror/423766  ../mirror/423771  ../mirror/423776
../mirror/423762  ../mirror/423767  ../mirror/423772  ../mirror/423777
../mirror/423763  ../mirror/423768  ../mirror/423773  ../mirror/423778

ठीक है, लेकिन शायद आप पूछ रहे हैं - लेकिन क्या अच्छा है? आप कैसे बता सकते हैं कि कौन सा है? आप यह भी सुनिश्चित कर सकते हैं कि आपने सही इनकोड संख्या को सही फ़ाइल नाम से जोड़ा है?

कुंआ...

echo "heyhey" >>./'    ' 
tgt=$(ls -id ./'    ')
cat ../mirror/${tgt%% .*} \
    $(ls -1td ../mirror/* | head -n1) 

आउटपुट

heyhey
heyhey

देखें, एक ही फ़ाइल के ../mirror/"${tgt%% .*}"संदर्भ में और अंदर संदर्भित दोनों इनकोड संख्या ./' '। वे एक ही फाइल का वर्णन करते हैं। वे इसे नाम देते हैं, लेकिन अधिक कुछ नहीं। कोई रहस्य नहीं है, वास्तव में, बस कुछ असुविधा जो आप अपने लिए कर सकते हैं, लेकिन अंत में आपके यूनिक्स फाइल सिस्टम के संचालन पर कोई प्रभाव नहीं पड़ेगा।

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.