RE: Help with a Python Program

  • From: BlueScale <bluescale1976@xxxxxxx>
  • To: programmingblind@xxxxxxxxxxxxx
  • Date: Wed, 08 Oct 2008 01:14:17 -0400

Thanks for the tip.  I'll go back to Google land and see what I can do
about re-writing it.
Thanks
On Tue, 2008-10-07 at 23:11 -0500, Ken Perry wrote:
>  
>  
> Just a hint on this code you can speed it up  a heck of a lot if you
> get away from dom and use sax or the simple template parser in python.
> Its not that important to speed up on a PC but I am currently coding
> on a PDA and this runs a bit slow do to the interpreter and the dom.
>  
> Ken
> 
> 
> 
> 
> ______________________________________________________________________
> From: programmingblind-bounce@xxxxxxxxxxxxx
> [mailto:programmingblind-bounce@xxxxxxxxxxxxx] On Behalf Of BlueScale
> Sent: Monday, October 06, 2008 10:39 PM
> To: programmingblind@xxxxxxxxxxxxx
> Subject: RE: Help with a Python Program
> 
> 
> 
> 
> Hi,
> Thanks for responding.  I actually just finished writing my own.  I
> never did get that code shrunk down to size, so I visited the Yahoo
> developer site and read through the documentation and code samples.
> It took a lot of trial and error, but I finally got it working!  I
> also learned a little more about Python in the process.
> If anyone else would like the code, here it is:
> #change zipCode to your zip code
> zipCode = 0
> def getWeather(zip_code):
>   if zip_code != 0:
>     import urllib
>     from xml.dom import minidom
>     WEATHER_URL = 'http://xml.weather.yahoo.com/forecastrss?p=%s'
>     WEATHER_NS = 'http://xml.weather.yahoo.com/ns/rss/1.0'
>     url = WEATHER_URL % zip_code
>     dom = minidom.parse(urllib.urlopen(url))
>     ycondition = dom.getElementsByTagNameNS(WEATHER_NS,
> 'condition')[0]
>     weatherReport = ycondition.getAttribute('temp') + ' | ' +
> ycondition.getAttribute('text')
>   else:
>     weatherReport = "No zip code set."
>   return weatherReport
> print getWeather(zipCode)
> 
> 
> 
> 
> On Mon, 2008-10-06 at 22:28 -0500, Ken Perry wrote: 
> 
> > This is pretty easy to do.  Unfortunately I am extremely busy right
> > this minute.  However if no one gets to you till Wednesday I will
> > get to it.  
> > Ken 
> > 
> > 
> > ____________________________________________________________________
> > 
> > From: programmingblind-bounce@xxxxxxxxxxxxx
> > [mailto:programmingblind-bounce@xxxxxxxxxxxxx] On Behalf Of
> > BlueScale
> > Sent: Sunday, October 05, 2008 10:39 PM
> > To: programmingblind@xxxxxxxxxxxxx
> > Subject: Help with a Python Program
> > 
> > 
> > 
> > Hi,
> > I found this program to get the weather with a commandline program.
> > I want to modify it for use inside another program, but every time I
> > do anything to it I end up breaking it.  I am still very new at
> > Python.  I would like it simplified quite a bit.  All I need is a
> > variable set at the top with a 5 digit zipcode, so it is easy to
> > modify.  I would like it to only return the current temp followed by
> > the current condition.  For example, when ran it should return
> > something like 78F | cloudy.  I need to remove the extended forecast
> > and the commandline arguments.  Can someone please help with this
> > and send me some info on how it was done? I thought it would be easy
> > to do but apparently I was wrong. *grin*  It would be even better if
> > the whole program could be simplified down to one function, but I am
> > not sure that will be possible.
> > Thanks for the help, and here is the code:
> > #! /usr/bin/python
> > 
> > """
> > Fetches weather reports from Yahoo!
> > 
> > Written by Thomas Upton (http://thomas.fiveuptons.com/),
> > with contributions from Chris Lasher
> > (http://igotgenes.blogspot.com/).
> > 
> > This code is licensed under a BY-NC-SA Creative Commons license.
> > http://creativecommons.org/licenses/by-nc-sa/3.0/us/
> > """
> > 
> > import sys
> > import urllib
> > from optparse import OptionParser
> > from xml.dom.minidom import parse
> > 
> > # Yahoo!'s limit on the number of days they will forecast for
> > DAYS_LIMIT = 2
> > WEATHER_URL = 'http://xml.weather.yahoo.com/forecastrss?p=%s'
> > WEATHER_NS = 'http://xml.weather.yahoo.com/ns/rss/1.0'
> > 
> > def get_weather(zip_code, days):
> >   """
> >   Fetches weather report from Yahoo!
> > 
> >   :Parameters:
> >   -`zip_code`: A five digit US zip code.
> >   -`days`: number of days to obtain forecasts for
> > 
> >   :Returns:
> >   -`weather_data`: a dictionary of weather data
> > 
> >   """
> > 
> >   # Get the correct weather url.
> >   url = WEATHER_URL % zip_code
> > 
> >   # Parse the XML feed.
> >   dom = parse(urllib.urlopen(url))
> > 
> >   # Get the units of the current feed.
> >   yunits = dom.getElementsByTagNameNS(WEATHER_NS, 'units')[0]
> > 
> >   # Get the location of the specified zip code.
> >   ylocation = dom.getElementsByTagNameNS(WEATHER_NS, 'location')[0]
> > 
> >   # Get the currrent conditions.
> >   ycondition = dom.getElementsByTagNameNS(WEATHER_NS,
> > 'condition')[0]
> > 
> >   # Hold the forecast in a hash.
> >   forecasts = []
> > 
> >   # Walk the DOM in order to find the forecast nodes.
> >   for i, node in enumerate(
> >           dom.getElementsByTagNameNS(WEATHER_NS,'forecast')):
> >       # Stop if the number of obtained forecasts equals the number
> > of requested days
> >       if i + 1 > days:
> >           break
> >       else:
> >           # Insert the forecast into the forcast dictionary.
> >           forecasts.append (
> >               {
> >                   'date': node.getAttribute('date'),
> >                   'low': node.getAttribute('low'),
> >                   'high': node.getAttribute('high'),
> >                   'condition': node.getAttribute('text')
> >               }
> >           )
> > 
> >   # Return a dictionary of the weather that we just parsed.
> >   weather_data = {
> >       'current_condition': ycondition.getAttribute('text'),
> >       'current_temp': ycondition.getAttribute('temp'),
> >       'forecasts': forecasts,
> >       'units': yunits.getAttribute('temperature'),
> >       'city': ylocation.getAttribute('city'),
> >       'region': ylocation.getAttribute('region'),
> >   }
> >   
> >   return weather_data
> > 
> > def create_report(weather_data, options):
> >   """
> >   Constructs a weather report as a string.
> > 
> >   :Parameters:
> >   -`weather_data`: a dictionary of weather data
> >   -`options`: options to determine output selections
> > 
> >   :Returns:
> >   -`report_str`: a formatted string reporting weather
> > 
> >   """
> > 
> >   report = []
> >   
> >   if options.location:
> >       if options.verbose:
> >           # Add the location header.
> >           report.append("Location:")
> > 
> >       # Add the location.
> >       location_string = "%(city)s, %(region)s\n" % weather_data
> >       report.append(location_string)
> > 
> >   if (not options.nocurr):
> >       if options.verbose:
> >           # Add current conditions header.
> >           report.append("Current conditions:")
> > 
> >       # Add the current weather.
> >       currstr = "%(current_temp)s%(units)s | %(current_condition)s
> > \n" % weather_data
> >       report.append(currstr)
> > 
> >   if (options.forecast > 0):
> >     if options.verbose:
> >         # Add the forecast header.
> >         report.append("Forecast:")
> > 
> >     # Add the forecasts.
> >     for forecast in weather_data['forecasts']:
> >       
> >         forecast['units'] = weather_data['units']
> >       
> >         forecast_str = """\
> >   %(date)s
> >     Low: %(low)s%(units)s
> >     High: %(high)s%(units)s
> >     Condition: %(condition)s
> >   """ % forecast
> > 
> >         report.append(forecast_str)
> > 
> >   report_str = "\n".join(report)
> >   
> >   return report_str
> > 
> > def create_cli_parser():
> >   """Creates a command line interface parser."""
> > 
> >   usage = (
> >       "%prog [options] zip_code",
> >       __doc__,
> >       """\
> > Arguments:
> >   ZIPCODE: The ZIP code for the region of interest.
> > """
> >   )
> >   
> >   usage = "\n\n".join(usage)
> >   
> >   cli_parser = OptionParser(usage)
> >   
> >   # Add the CLI options
> >   cli_parser.add_option('-c', '--nocurr', action='store_true',
> >       help="Suppress reporting the current weather conditions"
> >   )
> >   
> >   cli_parser.add_option('-f', '--forecast', action='store',
> > type='int',
> >       help="Show the forecast for DAYS days", metavar="DAYS")
> >   
> >   cli_parser.add_option('-l', '--location', action='store_true',
> >       help="Give the location of the weather"
> >   )
> >   
> >   cli_parser.add_option('-v', '--verbose', action='store_true',
> >       help="Print the weather section headers"
> >   )
> >   
> >   cli_parser.set_defaults(forecast=0)
> > 
> >   return cli_parser
> > 
> > def main(argv):
> > 
> >   # Create the command line parser.
> >   cli_parser = create_cli_parser()
> >   
> >   # Get the options and arguments.
> >   opts, args = cli_parser.parse_args(argv)
> > 
> >   # Check that an argument was passed.
> >   if len(args) < 1:
> >       cli_parser.error("Not enough arguments supplied.")
> > 
> >   # Check the zip code
> >   zip_code = args[0]
> >   
> >   if len(zip_code) != 5 or not zip_code.isdigit():
> >       cli_parser.error("ZIP code must be 5 digits")
> >   
> >   if opts.forecast > DAYS_LIMIT or opts.forecast < 0:
> >      cli_parser.error("Days to forecast must be between 0 and %d" %
> > DAYS_LIMIT)
> > 
> >   # Get the weather.
> >   weather = get_weather(zip_code, opts.forecast)
> > 
> >   # Create the report.
> >   report = create_report(weather, opts)
> > 
> >   print report
> > 
> > if __name__ == "__main__":
> >   main(sys.argv[1:]) 

Other related posts: