Re: [chirp_devel] [csv] Friendlier defaults for missing cToneFreq/rToneFreq columns in csv import - Fixes #1577
I don't mind changing it if I understand what to change it to. The current code was Tom's suggestion after I made the comment
I'd actually felt a little guilty about iterating the header line for every line in the file, but didn't see a way to factor that without creating globals, which I didn't think would be wanted.
I've said before I'm a bit of a newbie to both OOP and Python. The concepts of both on-the-fly addition of data items to an object, and conditionals on their existence (vice value) are new to me, and I just took it as the way it should be done.
I think you're saying that on-the-fly addition of data items to an object is not preferred style?
I do see that it could be initialized in the constructor (if that's the right term in Python) and so still not be a global, which is what I think you're saying.
By "when we start the load" do you mean in this clause in load(): if lineno == 1: header = line # add my test for rToneFreq/cToneFreq headers here continue
Would initializing my booleans to None in __init__ possibly end up raising an exception in some subclass with its own __init__() but not its own _clean_tmode()? Is that even asking a reasonable question? If not, ignore the next question.
Since my code doesn't do anything unless one is True and the other False, if I set them both in load(), would initializing them False in __init__() be more robust?
-dan
On Apr 27, 2014, at 6:23 PM, Dan Smith - dsmith@danplanet.com wrote:
I don't mean to nitpick, and I know I've ignored this for too long anyway. However, I don't really like this:
- def _clean_tmode(self, headers, line, mem):
""" If there is exactly one of [rToneFreq, cToneFreq] columns in the
csv file, use it for both rtone & ctone. Makes TSQL use friendlier."""
if not hasattr(self, "_file_has_rTone"):
self._file_has_rTone = "rToneFreq" in headers
if not hasattr(self, "_file_has_cTone"):
self._file_has_cTone = "cToneFreq" in headers
...because it modifies self in the middle of a method. Would you mind if we set those in __init__, perhaps just to None, and then set them True/False when we start the load?
If you don't want to spin it again, I'll just apply as-is and chalk it up to OCD, but I really think it'd be nicer.
--Dan
I've said before I'm a bit of a newbie to both OOP and Python. The concepts of both on-the-fly addition of data items to an object, and conditionals on their existence (vice value) are new to me, and I just took it as the way it should be done.
It's not wrong, it's just generally not preferred.
I think you're saying that on-the-fly addition of data items to an object is not preferred style?
Right, so the reasoning for this is that someone comes along later and sees that "oh, there is a self._file_has_header_foo property" and goes to use it in their separate method. However, if they don't realize that it was only added in the middle of your method, which seems like it only cleans things and isn't particularly structural, then they'll get a crash if they run before you run.
Initializing it to *something* in __init__ just helps avoid that situation. Note that pre-initializing things in a C-like way is very unpythonic, but in this case it's just a "safety for others" sort of thing. It's subtle, optional, and certainly open to opinion. However, when you have a bunch of different folks working on the same set of code, sometimes it helps to be a little more explicit about things like that.
What you're adding is somewhat of a predicate, which always has some value, even if "false until determined otherwise." That makes it even more reasonable (IMHO) to have it be defined in some way, even if the default state is "not sure yet, assume false" (i.e. the None case).
I do see that it could be initialized in the constructor (if that's the right term in Python) and so still not be a global, which is what I think you're saying.
Yep.
By "when we start the load" do you mean in this clause in load(): if lineno == 1: header = line # add my test for rToneFreq/cToneFreq headers here continue
Just set it once we know what it should be, which would be once we read the headers.
Would initializing my booleans to None in __init__ possibly end up raising an exception in some subclass with its own __init__() but not its own _clean_tmode()? Is that even asking a reasonable question? If not, ignore the next question.
Nope, the subclass should call the superclass' init, which will set them. If they're never used, that's fine, and there is no need for the subclass to pre- or post-define them in that case.
Again, python is super dynamic, as you saw from your use of modifying self there in the middle of your method. I'm not trying to scare you away from using the dynamic-ness, I just think that in this particular case, it's worth being more explicit.
Thanks for humoring me :P
--Dan
participants (2)
-
chirp.cordless@xoxy.net
-
Dan Smith