আমি কীভাবে স্পেসগুলিকে ভিএম বা লিনাক্সের ট্যাবগুলিতে রূপান্তর করতে পারি?


190

আমার কী প্রয়োজন তা না পেয়ে ফাঁকা স্থানগুলিকে ট্যাবগুলিতে কীভাবে রূপান্তর করা যায় তার জন্য স্ট্যাক ওভারফ্লোতে আমি বেশ কয়েকটি প্রশ্নের সন্ধান করেছি। ট্যাবগুলিকে কীভাবে স্থানগুলিতে রূপান্তর করা যায় সে সম্পর্কে আরও প্রশ্ন রয়েছে বলে মনে হয় তবে আমি তার বিপরীতটি করার চেষ্টা করছি।

ইন Vimআমি চেষ্টা করেছি :retabএবং :retab!ভাগ্য ছাড়া, কিন্তু আমি বিশ্বাস করে, তাদেরকে ট্যাবগুলি থেকে স্থানগুলি যাদের কাছে কোন পথে যাওয়ার জন্য আসলে।

আমি উভয় চেষ্টা করেছিলাম expandএবং unexpandকমান্ড প্রম্পটে কোনও ভাগ্য ছাড়াই।

এই প্রশ্নে ফাইলটি এখানে:

http://gdata-python-client.googlecode.com/hg-history/a9ed9edefd61a0ba0e18c43e448472051821003a/samples/docs/docs_v3_example.py

আমি কীভাবে শেল বা শেল ব্যবহার করে শীর্ষস্থানগুলিকে ট্যাবগুলিতে রূপান্তর করতে পারি Vim?


@ মোটের মন্তব্যে যা এখন মুছে ফেলা হয়েছে, তার প্রথম উদাহরণ ( sed "s/ +/`echo -e '\t'`/g" < input.py > output.py) প্রদর্শিত হয় কেবল স্থান স্থান নয়, সমস্ত স্থানকে রূপান্তরিত করে। দ্বিতীয় উদাহরণে ( sed "s/^ +/`echo -e '\t'`/g" < input.py > output.py) এটি কেবল প্রতিটি লাইনের প্রথম স্থানটিকে একটি ট্যাব দিয়ে প্রতিস্থাপন করে এবং বাকি অংশটি ছেড়ে দেয়।
cwd


আমি সমস্ত / বহু ফাইলের উত্তর খুঁজে পাইনি , তাই আমি নিজের একটি লিখেছি: stackoverflow.com/a/44581474/1115187 । সাথে find, awkএবং ব্ল্যাকজ্যাক (যদিও এটির মন্তব্যগুলিতে ছেড়ে দেওয়া খুব দীর্ঘ)
ম্যাক্সকরিউকভ

উত্তর:


314

সমস্ত নেতৃস্থানীয় স্পেসগুলি (এর চেয়ে আরও প্রশস্ত 'tabstop') প্রসারিত করার জন্য ভিম ব্যবহার করে আপনি ব্যবহার করতে সঠিক ছিলেন retabতবে প্রথমে নিশ্চিত হন 'expandtab'পুনরায় সেট করুন ( :verbose set ts? et?আপনার বন্ধু)। retabএকটি ব্যাপ্তি নেয় , তাই আমি সাধারণত %"সম্পূর্ণ ফাইল" বোঝাতে নির্দিষ্ট করি ।

:set tabstop=2      " To match the sample file
:set noexpandtab    " Use tabs, not spaces
:%retab!            " Retabulate the whole file

এই জাতীয় কিছু করার আগে (বিশেষত পাইথন ফাইলগুলির সাথে!), আমি সাধারণত সেট করি 'list', যাতে আমি সাদা স্থান এবং পরিবর্তন দেখতে পারি can

এর জন্য আমার.vimrc নিচের ম্যাপিংটি রয়েছে :

nnoremap    <F2> :<C-U>setlocal lcs=tab:>-,trail:-,eol:$ list! list? <CR>

2
এখানে আমি এটা কিভাবে কাজ পেয়েছি, নিশ্চিত না প্রয়োজনীয় আর কোনটা নয়, এবং BTW আমি জানি না কি reatab আগে "%" করছে: :set noet, :set tabstop=2, :retab!, :%retab!, :set tabstop=1, :retab!,:%retab!
cwd

2
আমি কেন ব্যবহার করি সে সম্পর্কে একটি ব্যাখ্যা অন্তর্ভুক্ত করার জন্য আমি আমার উত্তর আপডেট করেছি %এফ 2 ম্যাপিংটি যেমন টাইপ করা থাকে ঠিক তেমন হয়
জনসয়েব

7
এই নির্দিষ্ট ফাইলটির জন্য, আমি কেবল এটি করব::set noet ts=2 |%retab!
জনসয়েব

1
@ জনসয়েব ন্যায্য হতে, আমি ভুল ছিলাম: :%retab!এখনও কাজ করে। আমি সঙ্গে গুলিয়ে ফেলা হয়েছিল ==, ইত্যাদি যা আছে preserveindent সেটিং সম্মান করি।
আনক

1
কফিসিপি ফাইলটি ফাঁকা জায়গা থেকে ট্যাবগুলিতে রূপান্তর করতে আমি @ জনসিওয়েবের উত্তর অনুসরণ করে (.vimrc ফাইল যোগ করে) তবে পরিবর্তে একটি:set tabstop=4
মাইকুমাস

38

1 - আপনার যদি ফাঁকা জায়গা থাকে এবং ট্যাবগুলি চান।

প্রথমত, আপনাকে সিদ্ধান্ত নিতে হবে কতগুলি স্পেসে একটি একক ট্যাব থাকবে। এটি বলেছিল, ধরুন আপনার কাছে 4 টি স্পেস বা 8 টি শীর্ষস্থানীয় লাইন রয়েছে ... আপনি বুঝতে পারছেন যে আপনি সম্ভবত একটি ট্যাবকে 4 স্পেস করতে চান। এখন সেই তথ্য সহ, আপনি:

:set ts=4
:set noet
:%retab!

এখানে একটা সমস্যা আছে! কমান্ডগুলির এই অনুক্রমটি আপনার সমস্ত পাঠ্য সন্ধান করবে, কেবল রেখার শুরুতে ফাঁকা স্থান নয়। তার অর্থ একটি স্ট্রিং এর মতো: "Hey,␣this␣␣␣␣is␣4␣spaces"হয়ে যাবে "Hey,␣this⇥is␣4␣spaces", তবে তা নয়! এটি একটি ট্যাব !.

এই সামান্য সমস্যা সমাধানের জন্য আমি searchপরিবর্তে একটি পুনরায় সংশোধন করব retab

:%s/^\(^I*\)␣␣␣␣/\1^I/g

এই সন্ধানটি 4 টি স্পেস দ্বারা অনুসরণ করা যেকোনও ট্যাব দিয়ে শুরু হওয়া যে কোনও লাইনটির জন্য পুরো ফাইলটিতে সন্ধান করবে এবং এটি যে কোনও সংখ্যক ট্যাব এবং এক খুঁজে পাওয়া যাবে তার জন্য এটি প্রতিস্থাপন করবে।

দুর্ভাগ্যক্রমে, এটি একবারে চলবে না!

প্রথমে, ফাইলটির ফাঁকা জায়গা দিয়ে শুরু হওয়া লাইন থাকবে। অনুসন্ধানের পরে কেবল প্রথম 4 টি স্পেসকে একটি ট্যাবে রূপান্তরিত করা হবে এবং নিম্নলিখিতটি দেওয়া যাক ...

আপনাকে আদেশটি পুনরাবৃত্তি করতে হবে। কতবার? যতক্ষণ না আপনি একটি pattern not found। আমি প্রক্রিয়াটি স্বয়ংক্রিয় করার কোনও উপায় সম্পর্কে ভাবতে পারি না। তবে আপনি যদি:

`10@:`

আপনি সম্ভবত সম্পন্ন হয়েছে। এই কমান্ডটি 10 ​​বারের জন্য সর্বশেষ অনুসন্ধান / প্রতিস্থাপনের পুনরাবৃত্তি করে। এটি সম্ভবত আপনার প্রোগ্রামে অনেকগুলি ইনডেন্ট থাকবে না। যদি এটি থাকে তবে কেবল আবার পুনরাবৃত্তি করুন @@

এখন, উত্তরটি সম্পূর্ণ করার জন্য। আমি জানি আপনি বিপরীতে চেয়েছিলেন, তবে কখন কখন জিনিসগুলি পূর্বাবস্থায় ফেলার দরকার তা আপনি জানেন না।

2 - আপনার ট্যাব রয়েছে এবং স্পেস চান।

প্রথমে আপনি নিজের ট্যাবগুলিতে রূপান্তর করতে চান তা কতগুলি স্পেসে স্থির করুন decide বলুন আপনি প্রতিটি ট্যাবটি 2 স্পেস করতে চান। আপনি তারপর:

:set ts=2
:set et
:%retab!

স্ট্রিংগুলির সাথে এটি একই সমস্যা হবে। তবে স্ট্রিংগুলির অভ্যন্তরে হার্ড ট্যাব ব্যবহার না করার জন্য এটির আরও ভাল প্রোগ্রামিং শৈলী হিসাবে, আপনি আসলে এখানে খুব ভাল করছেন। আপনার যদি সত্যিই স্ট্রিংয়ের ভিতরে কোনও ট্যাব প্রয়োজন হয় তবে ব্যবহার করুন \t


একটি অত্যন্ত বিরল জাতি অবস্থা বলে মনে হচ্ছে। যাইহোক, ভিজ্যুয়াল-রেঞ্জ নির্বাচন গ্রহণ করে কোনও ফাংশন তৈরি করুন এবং কোনও মিল না পাওয়া পর্যন্ত অনুসন্ধান ফাংশন পুনরাবৃত্তি করুন, আমি অনুমান করি যে এটি আরও চতুর এবং দরকারী উত্তর হবে।
albfan

ইয়েস, বা যে। আপনি যদি আরও নির্দিষ্ট সমাধান চান তবে আপনি একটি ফাংশন ব্যবহার করতে পারেন। যাইহোক, এটি কীভাবে করবেন তা জেনে রাখা ভাল ex command, কারণ ফাংশনের অভ্যন্তরে এটিই হবে would এবং না, এটি বিরল নয়। গণ্ডগোলের জন্য আপনার কেবল ফাঁকা ফাঁকা স্ট্রিং থাকা দরকার। মোটেও বিরল নয়। আমি সেখানে আছি মন্তব্য করার জন্য ধন্যবাদ।
ডাঃ Beco

একাধিকবার অনুসন্ধান চালানোর পরিবর্তে, প্রতিটি লাইনের পরপর স্পেসের 4 টির সমস্ত গ্রুপকে ট্যাবগুলিতে রূপান্তর করতে কেন / জি যথেষ্ট নয় দয়া করে তা ব্যাখ্যা করুন।
বাজরতুর থরলেসিয়াস

হাই @ বিজার্টথরল্যাকিয়াস, সমস্যাটি হ'ল যদি আপনি ^চিহ্নটি সরিয়ে ফেলেন , লাইনটির শুরু থেকে অনুসন্ধান শুরু করতে, আপনি স্ট্রিংয়ের ভিতরে ফাঁকা স্থান পরিবর্তন করার ঝুঁকিপূর্ণ হবেন। সঙ্গে ^আপনি গ্যারান্টি আপনি শুধুমাত্র ফাঁকা স্থান এবং ট্যাব পরিবর্তন করা হয় লাইনের শুরু এভাবে খাঁজ থেকে। তদ্ব্যতীত, আপনি যদি নিশ্চিত হন যে একবারে সব করা ঠিক আছে, তবে সরান ^এবং কেবল একবারেই এটি চালান::%s/\(^I*\)␣␣␣␣/\1^I/g
ডঃ বেকো

14
:%s/\(^\s*\)\@<=    /\t/g

অনুবাদ: টানা 4 টি স্পেসের প্রতিটি দৃষ্টান্ত অনুসন্ধান করুন (= অক্ষরের পরে) তবে কেবলমাত্র সেই বিন্দুটি পর্যন্ত সম্পূর্ণ লাইনটি শ্বেত স্পেসে থাকে (এটি শূন্য-প্রস্থের চেহারা-পিছনের দৃ uses়তা ব্যবহার করে \@<=)। প্রতিটি পাওয়া উদাহরণটি একটি ট্যাব অক্ষরের সাথে প্রতিস্থাপন করুন।


1
একমাত্র সমাধান যে বিস্তৃত কাজ 1 স্থান থেকে 1 টি ট্যাব , কিন্তু উত্তর মধ্যে ইউনিকোড হুঁশিয়ার, আমি শুধু ব্যবহার করা :%s/\(^\s*\)\@<= /\t/g- (1 টি ট্যাব, 4 শূণ্যস্থান রাখা 4 শূণ্যস্থান রূপান্তর করতে) স্পেস যথাযথ সংখ্যা করা পরে<=
Orwellophile

5

সমস্ত স্পেসগুলি ট্যাবে পরিবর্তন করে:% s / \ s / \ t / g


এটি আমার যা প্রয়োজন ঠিক তা-ই। ধন্যবাদ। আমার কেবলমাত্র পরিবর্তনটি হ'ল প্রতি 4 স্পেস প্রতি একক স্পেস না করে ট্যাব দিয়ে প্রতিস্থাপন করা।
বেনামে ব্যক্তি

3

লিনাক্স: সাথে unexpand(এবং expand)

এখানে একটি খুব ভাল সমাধান: https://stackoverflow.com/a/11094620/1115187 , বেশিরভাগ ক্ষেত্রে এটি * নিক্স-ইউটিলিটিগুলি ব্যবহার করে:

  1. অব্যবস্থাপন - স্পেস -> ট্যাব
  2. প্রসারিত - ট্যাব -> স্পেস

লিনাক্স: কাস্টম স্ক্রিপ্ট

আমার আসল উত্তর

ফোল্ডারের সমস্ত ফাইলে (পুনরাবৃত্তভাবে) সমস্ত ফাইলের ট্যাব সহ 4- স্পেসস ইন্ডেন্টেশন ( {4}স্ক্রিপ্টে দুটি আছে) প্রতিস্থাপনের জন্য স্নিপেট বাশ করুন :.py./app

find ./app -iname '*.py' -type f \
    -exec awk -i inplace \
    '{ match($0, /^(( {4})*)(.*?)$/, arr); gsub(/ {4}/, "\t", arr[1]) }; { print arr[1] arr[3] }' {} \; 

এটি মাঝখানে বা শেষে 4-স্পেস পরিবর্তন করে না।

উবুন্টু 16.0x এবং লিনাক্স মিন্ট 18 এর অধীনে পরীক্ষা করা হয়েছিল


0

আমার ক্ষেত্রে, আমার একাধিক স্পেস ছিল (ক্ষেত্রগুলি এক বা একাধিক স্পেস দ্বারা পৃথক করা হয়েছিল) যা আমি একটি ট্যাব দ্বারা প্রতিস্থাপন করতে চেয়েছিলাম। নিম্নলিখিত এটি করেছে:

:% s/\s\+/\t/g

0

আপনি গনুহ coreutils ইনস্টল করা থাকে, বিবেচনা %!unexpand --first-onlyবা 4-স্পেস ট্যাব জন্য, বিবেচনা %!unexpand -t 4 --first-only( --first-onlyবর্তমান ধরো যদি আপনি দূর্ঘটনাক্রমে invoking হয়েছে unexpandসঙ্গে --all)।

দ্রষ্টব্য যে এটি কেবলমাত্র নির্ধারিত ট্যাব স্টপের আগের জায়গাগুলি প্রতিস্থাপন করবে, তাদের অনুসরণকারী স্পেসগুলি নয় ; আপনি ট্যাবগুলিকে আরও আক্ষরিকভাবে প্রদর্শন না করলে আপনি ভিমে কোনও ভিজ্যুয়াল পার্থক্য দেখতে পাবেন না; উদাহরণস্বরূপ, আমার ~/.vimrcধারণাগুলি set list listchars=tab:▸┈(আমি সন্দেহ করি যে এটি unexpandকাজ করে না বলে আপনি ভাবেন )।


0

2 স্পেস থেকে 4 স্পেসে ফাইলটি সেট করতে (উদাহরণস্বরূপ ডিরেক্টরি হায়ারার্কিতে সমস্ত * .ts ফাইলগুলি) পুনরায় সেট করতে ভিম ব্যবহার করতে আপনি কমান্ড লাইন থেকে এটি চেষ্টা করতে পারেন:

find . -name '*.ts' -print0 | xargs -0 -n1 vim -e '+set ts=2 noet | retab! | set ts=4 et | retab | wq'

এটি যা করছে তা হ'ল findসমস্ত মিলে যাওয়া ফাইলগুলিকে পাস করার জন্য xargs(নামটিতে ডাব্লু / স্পেসগুলি হ্যান্ডেল করার জন্য -0 প্রিন্ট0 বিকল্পটি xargs--তে বিকল্পের সাথে কাজ করে)।

-eবিদ্যমান লিডিং স্পেসগুলি ট্যাবগুলিতে পরিবর্তন করতে, ট্যাব স্টপটিকে পুনরায় সেট করা এবং ট্যাবগুলিকে ফাঁকা জায়গায় পরিবর্তন করা এবং অবশেষে সংরক্ষণ এবং প্রস্থানকরণের জন্য xargs প্রদত্ত প্রাক্তন কমান্ডটি কার্যকর করতে প্রতিটি ফাইলের উপর প্রিম মোডে ( ) চালায়।

প্রাক্তন মোডে চলমান এটি প্রতিরোধ করে: Vim: Warning: Input is not from a terminalপ্রতিটি ফাইলের জন্য।


-1

সাধারণ পাইথন লিপি:

import os

SOURCE_ROOT = "ROOT DIRECTORY - WILL CONVERT ALL UNDERNEATH"

for root, dirs, files in os.walk(SOURCE_ROOT):
    for f in files:
        fpath = os.path.join(root,f)
        assert os.path.exists(fpath)
        data = open(fpath, "r").read()
        data = data.replace("    ", "\t")
        outfile = open(fpath, "w")
        outfile.write(data)
        outfile.close()

একটি বিশাল সমস্যা: এই স্নিপেটটি সমস্ত 4-স্পেসকে প্রতিস্থাপন করে , কেবল ইন্ডেন্টেশন নয় (লাইনের শুরুতে)
ম্যাক্সকুরিউকভ

এবং দ্বিতীয়: ফাইল-ফিল্টার প্রয়োগ করা হয়নি
ম্যাক্সকুরিউকোভ
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.