কিভাবে একটি স্ট্রিং জিরো প্যাড?


1439

বামে শূন্যের সাথে সংখ্যার স্ট্রিং প্যাড করার পাইথোনিক উপায় কী, অর্থাত্ সংখ্যার স্ট্রিংটির একটি নির্দিষ্ট দৈর্ঘ্য রয়েছে?

উত্তর:


2388

স্ট্রিংস:

>>> n = '4'
>>> print(n.zfill(3))
004

এবং সংখ্যার জন্য:

>>> n = 4
>>> print(f'{n:03}') # Preferred method, python >= 3.6
004
>>> print('%03d' % n)
004
>>> print(format(n, '03')) # python >= 2.6
004
>>> print('{0:03d}'.format(n))  # python >= 2.6 + python 3
004
>>> print('{foo:03d}'.format(foo=n))  # python >= 2.6 + python 3
004
>>> print('{:03d}'.format(n))  # python >= 2.7 + python3
004

স্ট্রিং বিন্যাস ডকুমেন্টেশন


3
'ফ্লোট' টাইপের অবজেক্টের জন্য অজানা ফর্ম্যাট কোড 'ডি'।
সিইস টিমারম্যান

7
মন্তব্যগুলি python >= 2.6ভুল। এই সিনট্যাক্সটি কাজ করে না python >= 3। আপনি এটিতে পরিবর্তন করতে পারেন python < 3, তবে আমি কি পরিবর্তে সর্বদা বন্ধনী ব্যবহার এবং মন্তব্যগুলি পুরোপুরি বাদ দিতে (প্রস্তাবিত ব্যবহারকে উত্সাহিত করতে) পরামর্শ দিতে পারি?
জেসন আর। কমসস

4
নোট করুন যে আপনার বিন্যাসের স্ট্রিংগুলি সংখ্যায়িত করতে হবে না: '{:03d} {:03d}'.format(1, 2)স্পষ্টতই মানগুলি ক্রম অনুসারে বরাদ্দ করেছে।
ড্রাগন

1
@ জেসনআর.কুমবস: আমি ধরে নিয়েছি আপনার printবক্তব্যটি বোঝানো হয়েছিল , যখন printপাইথন 3 এ কোনও ফাংশন হওয়া উচিত ? আমি পেরেন্সে সম্পাদনা করেছি; যেহেতু শুধুমাত্র একটি জিনিস মুদ্রিত হচ্ছে, এটি এখন পাই 2 এবং পাই 3 এ অভিন্নভাবে কাজ করে।
শেডোএ্যাঞ্জার


352

কেবল স্ট্রিং অবজেক্টের রড পদ্ধতিটি ব্যবহার করুন ।

এই উদাহরণটি 10 ​​অক্ষরের দীর্ঘ স্ট্রিং তৈরি করবে, প্রয়োজনীয়ভাবে প্যাডিং করবে।

>>> t = 'test'
>>> t.rjust(10, '0')
>>> '000000test'

123

এছাড়াও zfill, আপনি সাধারণ স্ট্রিং ফর্ম্যাটিং ব্যবহার করতে পারেন:

print(f'{number:05d}') # (since Python 3.6), or
print('{:05d}'.format(number)) # or
print('{0:05d}'.format(number)) # or (explicit 0th positional arg. selection)
print('{n:05d}'.format(n=number)) # or (explicit `n` keyword arg. selection)
print(format(number, '05d'))

স্ট্রিং ফর্ম্যাটিং এবং এফ-স্ট্রিংয়ের জন্য ডকুমেন্টেশন ।


3
পিইপি 3101% কে কোনওভাবেই হ্রাস করা হয়েছে তা উল্লেখ করে না।
zwirbeltier

@Zwirbeltier PEP 3101 ব্যাখ্যা করে যে কীভাবে বিন্যাসটি ব্যবহার করতে হয়, এটি আমার অর্থ।
কনরাড রুডল্ফ

4
"সম্পাদনা" এখনও উল্লেখ করেছে "... বিন্যাসের এই পদ্ধতিটি অবচয় করা হয়েছে ..."।
zwirbeltier

1
@ জ্বির্বিলটিয়ার হ্যাঁ, এবং এটি অবহেলা করা হয়েছে। তবে এটি পিইপিতে সরাসরি বলা হয়নি। ডকুমেন্টেশনটি অবশ্য এর formatপরিবর্তে ব্যবহার করতে বলে এবং লোকেরা সাধারণত এটি হ্রাস করার উদ্দেশ্যে ব্যাখ্যা করে।
কনরাড রুডল্ফ

1
@ লার্শ এটি সন্ধানের জন্য ধন্যবাদ। সুতরাং তারা তফসিলের পিছনে পিছনে (পাইথন ৩.১ ভবিষ্যতে নয়, এটি অতীতের অতীতে)। এটি দেওয়া হলেও, আমি এখনও মনে করি না যে উত্তরটি বিভ্রান্তিকর ছিল, প্রতিবার পাইথন বিকাশের তফসিলটি নতুন, স্বেচ্ছাসেবীর দিকে পরিবর্তিত হয়ে কেবল কঠোরভাবে আপডেট করা হয়নি। যাইহোক, এটি আমাকে আমার উত্তর থেকে কিছু অপ্রাসঙ্গিক এবং পুরানো সামগ্রী সরিয়ে দেওয়ার সুযোগ দিয়েছে gave
কনরাড রুডলফ

62

পাইথন 3.6+ এর জন্য এফ-স্ট্রিংগুলি ব্যবহার করে:

>>> i = 1
>>> f"{i:0>2}"  # Works for both numbers and strings.
'01'
>>> f"{i:02}"  # Works only for numbers.
'01'

পাইথন 2 থেকে পাইথন 3.5:

>>> "{:0>2}".format("1")  # Works for both numbers and strings.
'01'
>>> "{:02}".format(1)  # Works only for numbers.
'01'


39

str(n).zfill(width)সঙ্গে কাজ করবে stringএস, intগুলি, floatগুলি ... এবং পাইথন 2. এক্স এবং 3. এক্স সামঞ্জস্যপূর্ণ:

>>> n = 3
>>> str(n).zfill(5)
'00003'
>>> n = '3'
>>> str(n).zfill(5)
'00003'
>>> n = '3.0'
>>> str(n).zfill(5)
'003.0'

23

যারা এখানে এসেছেন তাদের জন্য কেবল একটি দ্রুত উত্তর নয়। আমি বিশেষত সময়ের স্ট্রিংয়ের জন্য এগুলি করি:

hour = 4
minute = 3
"{:0>2}:{:0>2}".format(hour,minute)
# prints 04:03

"{:0>3}:{:0>5}".format(hour,minute)
# prints '004:00003'

"{:0<3}:{:0<5}".format(hour,minute)
# prints '400:30000'

"{:$<3}:{:#<5}".format(hour,minute)
# prints '4$$:3####'

"0" চিহ্নগুলি "2" প্যাডিং অক্ষরগুলির সাথে কী প্রতিস্থাপন করবে তা ডিফল্ট একটি খালি স্থান

">" চিহ্নগুলি সমস্ত "" 0 "অক্ষরটিকে স্ট্রিংয়ের বামে সংযুক্ত করে

":" ফর্ম্যাট_স্পেক প্রতীক


23

বামদিকে শূন্যের সাথে সংখ্যার স্ট্রিং প্যাড করার সর্বাধিক অজগর উপায় কী, তাই সংখ্যার স্ট্রিংটির একটি নির্দিষ্ট দৈর্ঘ্য থাকে?

str.zfill এটি করার জন্য বিশেষভাবে উদ্দেশ্য:

>>> '1'.zfill(4)
'0001'

নোট করুন যে এটি বিশেষভাবে অনুরোধ অনুযায়ী সংখ্যাযুক্ত স্ট্রিংগুলি পরিচালনা করার উদ্দেশ্যে এবং স্ট্রিংয়ের শুরুতে একটি +বা সরানো -:

>>> '+1'.zfill(4)
'+001'
>>> '-1'.zfill(4)
'-001'

এখানে সহায়তা দেওয়া আছে str.zfill:

>>> help(str.zfill)
Help on method_descriptor:

zfill(...)
    S.zfill(width) -> str

    Pad a numeric string S with zeros on the left, to fill a field
    of the specified width. The string S is never truncated.

কর্মক্ষমতা

এটি বিকল্প পদ্ধতির সর্বাধিক সম্পাদনকারী:

>>> min(timeit.repeat(lambda: '1'.zfill(4)))
0.18824880896136165
>>> min(timeit.repeat(lambda: '1'.rjust(4, '0')))
0.2104538488201797
>>> min(timeit.repeat(lambda: f'{1:04}'))
0.32585487607866526
>>> min(timeit.repeat(lambda: '{:04}'.format(1)))
0.34988890308886766

%পদ্ধতির জন্য আপেলের সাথে আপেলকে সর্বোত্তম তুলনা করতে (নোট করুন এটি আসলে ধীরে ধীরে), যা অন্যথায় প্রাক-গণনা করবে:

>>> min(timeit.repeat(lambda: '1'.zfill(0 or 4)))
0.19728074967861176
>>> min(timeit.repeat(lambda: '%04d' % (0 or 1)))
0.2347015216946602

বাস্তবায়ন

কিছুটা খনন করে, আমি zfillপদ্ধতিটির প্রয়োগটি এখানে পেয়েছি Objects/stringlib/transmogrify.h:

static PyObject *
stringlib_zfill(PyObject *self, PyObject *args)
{
    Py_ssize_t fill;
    PyObject *s;
    char *p;
    Py_ssize_t width;

    if (!PyArg_ParseTuple(args, "n:zfill", &width))
        return NULL;

    if (STRINGLIB_LEN(self) >= width) {
        return return_self(self);
    }

    fill = width - STRINGLIB_LEN(self);

    s = pad(self, fill, 0, '0');

    if (s == NULL)
        return NULL;

    p = STRINGLIB_STR(s);
    if (p[fill] == '+' || p[fill] == '-') {
        /* move sign to beginning of string */
        p[0] = p[fill];
        p[fill] = '0';
    }

    return s;
}

আসুন এই সি কোড দিয়ে চলুন।

এটি প্রথমে অবস্থানগতভাবে যুক্তিকে পার্স করে, অর্থ এটি কীওয়ার্ড আর্গুমেন্টকে মঞ্জুরি দেয় না:

>>> '1'.zfill(width=4)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
TypeError: zfill() takes no keyword arguments

এটি এটি একই দৈর্ঘ্য বা তার চেয়ে বেশি দীর্ঘ কিনা তা পরীক্ষা করে which

>>> '1'.zfill(0)
'1'

zfillকল pad(এই padফাংশন এছাড়াও দ্বারা বলা হয় ljust, rjustএবং centerসেইসাথে)। এটি মূলত বিষয়বস্তুগুলিকে একটি নতুন স্ট্রিংয়ে অনুলিপি করে এবং প্যাডিংয়ে পূরণ করে।

static inline PyObject *
pad(PyObject *self, Py_ssize_t left, Py_ssize_t right, char fill)
{
    PyObject *u;

    if (left < 0)
        left = 0;
    if (right < 0)
        right = 0;

    if (left == 0 && right == 0) {
        return return_self(self);
    }

    u = STRINGLIB_NEW(NULL, left + STRINGLIB_LEN(self) + right);
    if (u) {
        if (left)
            memset(STRINGLIB_STR(u), fill, left);
        memcpy(STRINGLIB_STR(u) + left,
               STRINGLIB_STR(self),
               STRINGLIB_LEN(self));
        if (right)
            memset(STRINGLIB_STR(u) + left + STRINGLIB_LEN(self),
                   fill, right);
    }

    return u;
}

কল করার পরে pad, zfillপূর্বের কোনওটি +বা -স্ট্রিংয়ের শুরুতে সরানো হয়।

নোট করুন যে মূল স্ট্রিংয়ের জন্য আসলে সংখ্যার প্রয়োজন হয় না:

>>> '+foo'.zfill(10)
'+000000foo'
>>> '-foo'.zfill(10)
'-000000foo'

পারফরম্যান্সের জন্য, এফ স্ট্রিংগুলি পাইথন 2 বনাম পাইথন 3 এর ক্ষেত্রে ব্যবহারের ক্ষেত্রে আরও ভাল রয়েছে? এছাড়াও, আমি মনে করি যে জিলফিল সাধারণ না হওয়ায় এটি আপনার উত্তরটিকে ডক্সের সাথে একটি লিঙ্ক রাখতে সহায়তা করবে
ইলাদ রৌপ্য

এবং এল্যাডসিলভার আপনার ব্যবহারের উপর নির্ভর করে +এবং এর সাথে আচরণের কথা মাথায় রেখে -এবং আমি ডক্সে একটি লিঙ্ক যুক্ত করেছি!
হারুন হলের

17
width = 10
x = 5
print "%0*d" % (width, x)
> 0000000005

সমস্ত উত্তেজনাপূর্ণ বিবরণের জন্য মুদ্রণ ডকুমেন্টেশন দেখুন!

পাইথন 3.x এর জন্য আপডেট (7.5 বছর পরে)

শেষ লাইনটি এখন হওয়া উচিত:

print("%0*d" % (width, x))

অর্থাত্ print()এখন একটি ফাংশন, বিবৃতি নয়। নোট করুন যে আমি এখনও ওল্ড স্কুল printf()স্টাইল পছন্দ করি কারণ আইএমএনএসএইচও, এটি আরও ভাল পড়ে এবং কারণ ওম, আমি ১৯৮০ সালের জানুয়ারী থেকে এই স্বরলিপিটি ব্যবহার করছি Some কিছু ... পুরানো কুকুর .. কিছু নতুন কৌশল।


1980 সাল থেকে ... তাই আপনি 60 বছরের পুরনো প্রোগ্রামার ... আপনি কী দয়া "%0*d" % (width, x)করে অজগর দ্বারা ব্যাখ্যা করা যায় সে সম্পর্কে আরও ব্যাখ্যা দিতে পারেন ?
লি

15

পাইথন ব্যবহার করার সময় >= 3.6, সবচেয়ে পরিষ্কার উপায় স্ট্রিং ফর্ম্যাটিং সহ এফ-স্ট্রিংগুলি ব্যবহার করা :

>>> s = f"{1:08}"  # inline with int
>>> s
'00000001'
>>> s = f"{'1':0>8}"  # inline with str
>>> s
'00000001'
>>> n = 1
>>> s = f"{n:08}"  # int variable
>>> s
'00000001'
>>> c = "1"
>>> s = f"{c:0>8}"  # str variable
>>> s
'00000001'

আমি একটির সাথে ফর্ম্যাট করতে পছন্দ করব int, কেবল তখনই সাইনটি সঠিকভাবে পরিচালনা করা হয়:

>>> f"{-1:08}"
'-0000001'

>>> f"{1:+08}"
'+0000001'

>>> f"{'-1':0>8}"
'000000-1'

নতুন সিনট্যাক্স উদাহরণের জন্য ধন্যবাদ। ভর্তি চর 'x' হবে: v = "A18"; s = f '; v: x> 8}' + "|"; বা s = v.ljust (8, "x") + "|";
চার্লি

@ চারলি that এটা আমার কাছে প্রশ্ন বা কেবল বিবৃতি ছিল?
রুহোলা

শুধু একটি বিবৃতি। আরও কিছু ব্যবহার পরীক্ষিত।
চার্লি 木匠

4

পূর্ণসংখ্যার হিসাবে সংরক্ষণ করা জিপ কোডগুলির জন্য:

>>> a = 6340
>>> b = 90210
>>> print '%05d' % a
06340
>>> print '%05d' % b
90210

1
আপনি সঠিক, এবং আমি যফিলের সাথে আপনার পরামর্শটি আরও ভালভাবেই পছন্দ করি

3

দ্রুত সময়ের তুলনা:

setup = '''
from random import randint
def test_1():
    num = randint(0,1000000)
    return str(num).zfill(7)
def test_2():
    num = randint(0,1000000)
    return format(num, '07')
def test_3():
    num = randint(0,1000000)
    return '{0:07d}'.format(num)
def test_4():
    num = randint(0,1000000)
    return format(num, '07d')
def test_5():
    num = randint(0,1000000)
    return '{:07d}'.format(num)
def test_6():
    num = randint(0,1000000)
    return '{x:07d}'.format(x=num)
def test_7():
    num = randint(0,1000000)
    return str(num).rjust(7, '0')
'''
import timeit
print timeit.Timer("test_1()", setup=setup).repeat(3, 900000)
print timeit.Timer("test_2()", setup=setup).repeat(3, 900000)
print timeit.Timer("test_3()", setup=setup).repeat(3, 900000)
print timeit.Timer("test_4()", setup=setup).repeat(3, 900000)
print timeit.Timer("test_5()", setup=setup).repeat(3, 900000)
print timeit.Timer("test_6()", setup=setup).repeat(3, 900000)
print timeit.Timer("test_7()", setup=setup).repeat(3, 900000)


> [2.281613943830961, 2.2719342631547077, 2.261691106209631]
> [2.311480238815406, 2.318420542148333, 2.3552384305184493]
> [2.3824197456864304, 2.3457239951596485, 2.3353268829498646]
> [2.312442972404032, 2.318053102249902, 2.3054072168069872]
> [2.3482314132374853, 2.3403386400002475, 2.330108825844775]
> [2.424549090688892, 2.4346475296851438, 2.429691196530058]
> [2.3259756401716487, 2.333549212826732, 2.32049893822186]

আমি বিভিন্ন পুনরাবৃত্তির বিভিন্ন পরীক্ষা করেছি। পার্থক্যগুলি বিশাল নয়, তবে সমস্ত পরীক্ষায় zfillসমাধানটি সবচেয়ে দ্রুত ছিল।


1

আর একটি পদ্ধতির দৈর্ঘ্যের জন্য শর্ত যাচাইয়ের সাথে তালিকার বোঝাপড়া ব্যবহার করা হবে। নীচে একটি বিক্ষোভ প্রদর্শন করা হচ্ছে:

# input list of strings that we want to prepend zeros
In [71]: list_of_str = ["101010", "10101010", "11110", "0000"]

# prepend zeros to make each string to length 8, if length of string is less than 8
In [83]: ["0"*(8-len(s)) + s if len(s) < desired_len else s for s in list_of_str]
Out[83]: ['00101010', '10101010', '00011110', '00000000']

0

ঠিক আছে:

 h = 2
 m = 7
 s = 3
 print("%02d:%02d:%02d" % (h, m, s))

সুতরাং আউটপুট হবে: "02:07:03"


-2

আপনি "0" পুনরাবৃত্তিও করতে পারেন, এটিকে প্রেন্ডিং করতে str(n)এবং ডানদিকের প্রস্থের স্লাইস পেতে পারেন। দ্রুত এবং নোংরা সামান্য অভিব্যক্তি।

def pad_left(n, width, pad="0"):
    return ((pad * width) + str(n))[-width:]

1
এটি কেবল ধনাত্মক সংখ্যার জন্যই কাজ করে। আপনি যদি negativeণাত্মক চান তবে এটি কিছুটা জটিল হয়ে যায়। তবে এই অভিব্যক্তিটি দ্রুত এবং নোংরা কাজের জন্য ভাল, যদি আপনি এই ধরণের জিনিস মনে না করেন।
জে লাকার

কেন এটিকে নিম্নমানের করা হয়েছে তা আমার সম্পূর্ণ ধারণা নেই। যদি এটির কারণ হয় তবে এটি নেতিবাচক সংখ্যাগুলিতে যথাযথভাবে কাজ করে না, তবে জিরোসের সাথে প্যাড ছাড়ার অপ্রতিরোধ্য কারণটি হল আইডি সংখ্যার জন্য। আপনার যদি নেতিবাচক আইডি নম্বর থাকে তবে আমার মনে হয় আপনার আরও বড় সমস্যা আছে ... আপনি কী আপনার প্যাডটি '00000-1234' ফর্মের প্রত্যাশা করছেন? বা '-000001234'? সত্য উত্তর দিয়ে এই উত্তরটি কার্যকরভাবে উত্তর দেয়, এটি সহজ, এটি পরিষ্কার, এটি এক্সটেনসিবল। এটি জফিল নাও হতে পারে তবে যদি এটির প্রশ্নের উত্তর দেয় তবে তা উর্ধ্বে দেওয়া উচিত।
টেস্টিস্লোকুকার
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.