Beginner: Data type conversion question

F

flagg

I am still fairly new to python and programming in general. My
question is regarding data conversion, I am working on a script that
will edit dns zone files, one of the functions i wrote handles
updating the serial number.
Our zone files use the date as the first part of the serial and a two
digit integer as the last two.

i.e. 2009011501. The next update would be 2009011502, etc
Here is the function I wrote, I am using dnspython for reading in zone
files as Zone "objects". Because dnspython's built-in serial updater
will not work with how we format our serial's, I have to re-write it.

def checkSerial():
"""
Checks the current 'date' portion of the serial number and
checks the current 'counter'(the two digit number at the end of
the serial number), then returns a complete new serial
"""
currentDate = time.strftime("%Y""%m""%d", time.localtime())
for (name, ttl, rdata) in zone.iterate_rdatas(SOA):
date = str(rdata.serial)[0:8]
inc = str(rdata.serial)[8:10]
if date == currentDate:
int(inc) + 1
print inc
newInc = str(inc).zfill(2)
serial = date + newInc
print "date is the same"
return serial
elif date < currentDate:
newInc = "01".zfill(2)
serial = currentDate + newInc
print "date is different"
return serial

Through all of this I am doing a lot of data type conversion. string -
integer, integer back to string, etc. Is this an efficient way of
handling this? I have to perform basic addition on the "inc"
variable, but also need to expose that value as a string. What I
have above does work, but I can't help but think there is a more
efficient way. I guess I am not used to data types being converted so
easily.
 
F

flagg

I am still fairly new to python and programming in general.  My
question is regarding data conversion, I am working on a script that
will edit dns zone files, one of the functions i wrote handles
updating the serial number.
Our zone files use the date as the first part of the serial and a two
digit integer as the last two.
i.e. 2009011501.  The next update would be 2009011502, etc
Here is the function I wrote, I am using dnspython for reading in zone
files as Zone "objects".  Because dnspython's built-in serial updater
will not work with how we format our serial's, I have to re-write it.
def checkSerial():
   """
   Checks the current 'date' portion of the serial number and
   checks the current 'counter'(the two digit number at the end of
   the serial number), then returns a complete new serial
   """
   currentDate =  time.strftime("%Y""%m""%d", time.localtime())
   for (name, ttl, rdata) in zone.iterate_rdatas(SOA):
       date = str(rdata.serial)[0:8]
       inc = str(rdata.serial)[8:10]
   if date == currentDate:
       int(inc) + 1

The previous line is pointless. It's like having '4+4' as a statement
on its own line. It calculates a value but doesn't change any state or
even use the value. Perhaps you instead meant?:
            inc = int(inc) + 1

Cheers,
Chris

Ah thank you. Oversight on my part. That explains why that if
statement never incremented the counter correctly. Anything odd about
how I'm converting back and forth between different data types as
often as I am? Is that common practice is normal programming?
(forgive the beginner questions)
 
M

Marc 'BlackJack' Rintsch

def checkSerial():
"""
Checks the current 'date' portion of the serial number and checks
the current 'counter'(the two digit number at the end of the serial
number), then returns a complete new serial """
currentDate = time.strftime("%Y""%m""%d", time.localtime())

The format string can be written as *one* string literal instead of
three: "%Y%m%d".
for (name, ttl, rdata) in zone.iterate_rdatas(SOA):
date = str(rdata.serial)[0:8]
inc = str(rdata.serial)[8:10]

Here you are converting `rdata.serial` twice.

tmp = str(rdata.serial)
date = tmp[0:8]
inc = int(tmp[8:10])

As `inc` is conceptually a number, you should do the conversion here and
treat it as number from now on.
if date == currentDate:
int(inc) + 1
print inc
newInc = str(inc).zfill(2)
serial = date + newInc
print "date is the same"
return serial
elif date < currentDate:
newInc = "01".zfill(2)
serial = currentDate + newInc
print "date is different"
return serial

Both branches do almost the same. You should try to avoid such code
duplication.

if date == currentDate:
inc += 1
elif date < currentDate:
inc = 1
else:
assert False # Should never happen.

return "%s%02d" % (date, inc)

That's it.

Ciao,
Marc 'BlackJack' Rintsch
 
K

Krishnakant

hello,
I am writing a twisted based rpc service where I am implementing a
complete application as a service.
I have many modules which make a package. Now when we publish a service
in twisted, we have to create one instance of a certain class and then
publish it with the help of reactor.
but in my application, there are more than one class in different .py
files. Now I want to know how do i create a package where all the
classes in different modules get published so that the entire package
can be used as the rpc server application and the client can be used to
query any module.

for example I have classes to get and set vendor, product, bills etc.
now all this has to be accessed through the xml rpc service.
Can some one tell me how to manage the entire twisted package as a
service.
happy hacking.
Krishnakant.
 
F

flagg

flagg said:
I am still fairly new to python and programming in general.  My
question is regardingdataconversion, I am working on a script that
will edit dns zone files, one of the functions i wrote handles
updating the serial number.
Our zone files use the date as the first part of the serial and a two
digit integer as the last two.
i.e. 2009011501.  The next update would be 2009011502, etc
Here is the function I wrote, I am using dnspython for reading in zone
files as Zone "objects".  Because dnspython's built-in serial updater
will not work with how we format our serial's, I have to re-write it.
def checkSerial():
    """
    Checks the current 'date' portion of the serial number and
    checks the current 'counter'(the two digit number at the end of
    the serial number), then returns a complete new serial
    """
    currentDate =  time.strftime("%Y""%m""%d", time.localtime())
    for (name, ttl, rdata) in zone.iterate_rdatas(SOA):
        date = str(rdata.serial)[0:8]
        inc = str(rdata.serial)[8:10]

If rdate.serial is already a string, as name would imply, the str() call
is pointless.  If not, can you get inc as int more directly?


    if date == currentDate:
        int(inc) + 1
        print inc
        newInc = str(inc).zfill(2)
        serial = date + newInc
        print "date is the same"
        return serial
    elif date < currentDate:
        newInc = "01".zfill(2)
        serial = currentDate + newInc
        print "date is different"
        return serial
Through all of this I am doing a lot ofdatatypeconversion. string -
handling this?  I have to perform basic addition on the "inc"
variable, but also need to expose that value as a string.   What I
have above does work, but I can't help but think there is a more
efficient way. I guess I am not used todatatypes being converted so
easily.

Other than that, you are perhaps worrying too much, even if code could
be squeezed more.  The idea that every object knows how to convert
itself to a string representation is basic to Python.

tjr

Actually when i run a type(serial) on that variable it returns a
"long" which i am not sure why dnspython uses a long variable to
store the serial. But you could be right about me worrying to much.
The other languages I have dabbled in (java, perl) I don't remember
type conversion being as simple. But again I am still new, so don't
quote me on that :)
 
F

flagg

def checkSerial():
    """
    Checks the current 'date' portion of the serial number and checks
    the current 'counter'(the two digit number at the end of the serial
    number), then returns a complete new serial """
    currentDate =  time.strftime("%Y""%m""%d", time.localtime())

The format string can be written as *one* string literal instead of
three: "%Y%m%d".
    for (name, ttl, rdata) in zone.iterate_rdatas(SOA):
        date = str(rdata.serial)[0:8]
        inc = str(rdata.serial)[8:10]

Here you are converting `rdata.serial` twice.

          tmp = str(rdata.serial)
          date = tmp[0:8]
          inc = int(tmp[8:10])

As `inc` is conceptually a number, you should do theconversionhere and
treat it as number from now on.
    if date == currentDate:
        int(inc) + 1
        print inc
        newInc = str(inc).zfill(2)
        serial = date + newInc
        print "date is the same"
        return serial
    elif date < currentDate:
        newInc = "01".zfill(2)
        serial = currentDate + newInc
        print "date is different"
        return serial

Both branches do almost the same.  You should try to avoid such code
duplication.

      if date == currentDate:
          inc += 1
      elif date < currentDate:
          inc = 1
      else:
          assert False   # Should never happen.

      return "%s%02d" % (date, inc)

That's it.

Ciao,
        Marc 'BlackJack' Rintsch

Ah

return "%s%02d" % (date, inc)


This piece is what I was missing in my original design. I couldn't
figure out hot to take and integer and force it to my double digit.
i.e. 01 instead of 1. Which is why I was using strings to make that
happen. (obviously incorrectly). Thanks

Could you explain what "assert" does in the if statement. I am
assuming if the first two conditions are not met, it will hit "assert
false" and exit the program?
 
T

Terry Reedy

flagg said:
....
Actually when i run a type(serial) on that variable it returns a
"long"

Then inc = serial % 100 is 'more directly'.
which i am not sure why dnspython uses a long variable to
store the serial.

Perhaps a holdever from C code where long is necessary to dependably
hold counts with 8 decimal digits.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,755
Messages
2,569,536
Members
45,007
Latest member
obedient dusk

Latest Threads

Top