Win a copy of Learn Java with Math: Using Fun Projects and Games this week in the Beginning Java forum!

Derik Davenport

Ranch Hand
+ Follow
since May 30, 2011
Cows and Likes
Cows
Total received
0
In last 30 days
0
Total given
0
Likes
Total received
5
Received in last 30 days
0
Total given
9
Given in last 30 days
0
Forums and Threads
Scavenger Hunt
expand Ranch Hand Scavenger Hunt
expand Greenhorn Scavenger Hunt

Recent posts by Derik Davenport


@Norm Radder: making the method static wouldn't help. More often than not I need to pass an instance of the interface to a library class. For example where myFilter is the class I am discussing here, and myDirectory is an instance of File. I must instantiate the class to pass it to the listFiles() method. But it seems weird to keep creating new instances of this class. Of course, creating the class is trivial since it has no constructor (uses Object's no arg constructor) and no state variables (not even final ones). It seems that once it loaded the first time every instance should use that same instance of the class.

It feels like String in a way.
It would generally be considered bad form to do this.
In that code alpha and beta are the same value, but they are different instances of the same value. It would be confusing to write it that way.



@Salil Wadnerkar:
I am not sure how this helps testing, but I am genuinely interested in finding out, if you have the time or can point me in the correct direction. If I instantiate the class from inside the function, I have no way to inject a mock. Right? (sorry if that doesn't make sense - I am not familiar with testing terminology). Also, wouldn't I test the FileFilter implementation by itself? And then the test the file that uses my implementation separately? Assuming the client is code is something I maintain, why would I want to inject a broken version of the filter?

3 years ago
I have a stateless class which implements a functional interface, FileFilter.
The same class is used in half a dozen places throughout the program.

It gets used in file finder dialog boxes, and also just to evaluate files from a directory listing.

Should I be creating a new instance of this class every time it is needed?
Should I create a Singleton with an instance method?
Should I just put this in a public static field of a utility class?

They all take the same amount of code space. Performance is not really an issue in my application. None of these choices is bad for me. But I wonder what experienced programmers do in this situation.





3 years ago
Mike Matthews,
I would say that you have already answered your own question. Yes, BigDecimal is overkill for your situation because it makes your code harder to read, harder to understand, and harder to debug. Your task is to convert from cubic centimeters (an integer) to cubic meters which will probably not be an integer.
Your first solution was to use a float; but that gave you aesthetically displeasing rounding errors. Look at the Formatter class. The rounding errors of floating point arithmetic still exist, but they will never be visible to end user.

If you don't like Formatter, you could consider fixed point arithmetic to avoid the rounding errors. http://en.wikipedia.org/wiki/Fixed-point_arithmetic

Is it ever necessary to use Big Decimals? Yes, whenever doing so makes your code easier to read. There has been an excellent discussion here about performance issues of BigDecimal versus other things. But I don't think you need to worry about that for a utility app like the one you are writing. Instead I would focus on clarity of code.


4 years ago

Aaron Shawlington wrote:I think it's very likely that you should take your difficulties as a design smell - i.e. rethink your wider design, rather than trying to hack the existing one to make it work.

I agree. It is possible that some creative refactoring would solve my problem.. You asked 'Does the parser need to construct the Generator'. No, but in this example I have stipulated that it must use one. But perhaps there is a way to refactor so that I don't need to use one, or that the methods that rely on Generator could be grouped in Generator on within a class that contains a generator. I would have to think about it in terms of a real world example.

It violates the Liskov substitution principle for a start - and that's a very sensible principle 99% of the time.

I am not sure I understand the application of Liskov very well. I once believed that it just meant that I shouldn't be allowed to create a subclass that made the method of a parent class have a more restrictive scope or throw an exception not thrown by the parent class. And that doesn't really apply. I did a quick google on Liskov and found that some people interpret it much more liberally. For some people, overriding any method would be a violation. Whatever the correct interpretation of Liskov is, my problem would still exist if the child class had not overriden any methods of the parent (abstract) class.

In my original code I made the parent class abstract so that this would not be an issue. Moreover, I created an Interface for the Parent class. When I created that interface, it was my intention to state that usage of any instance of any concrete class (a subclass of AbstractMessageParser) would be accessed only through the interface. I am genuinely unsure of how to apply Liskov to that condition. Clearly, if I made HtmlParser derive from SmtpParser, then yes, that would certainly fail some kind of smell test. Is that Liskov?

4 years ago

Campbell Ritchie wrote:Will this work?


Campbell,
The very first time I ran into this pattern (the need to override fields in a sub-class) that is exactly how I solved it. It blew up in my face about a year later.
Ever since then I have been using dependency Injection like I demonstrated in my original post. But I have had a few instances recently where the pattern fails for one or both of the 2 reasons I cited. It has happened 3 times in the last 2 weeks that I had one of those 2 problems.
4 years ago

Campbell Ritchie wrote:No, you can't You can't override fields;
...
Don't go hiding fields; that way lies confusion and errors.

Thanks for contributing... I hope <fingers crossed> it was obvious in my posting that I already knew that I couldn't override a field and that I didn't want to have hidden fields either. I was trying to describe the problem and then describe the type of solution that I was hoping to find. The code I provided was a pedagogical example for that purpose, not exemplary code.

You initialise fields with the constructor and you initialise superclass fields with the super(...);

I did discuss that solution and the problems associated with it.

If there are lots of fields, create an object which encapsulates all their values.

As I said, that is a good solution for problem #1 of 2. If I defined the enum (good suggestion) or the Map in the parent class (or interface) then I could avoid a parallel hierarchy and keep the constants tied to the main parser hierarchy classes.

And so should whoever told you to call them child classes

LOL! I am guilty of anthropomorphising my classes. I have sibling classes (both derive directly from the same base class) and cousin classes too. YOu will know I have lost it when I start attributing gender.
4 years ago
Welcome to JavaRanch,

It is not one or the other. It is a matter of degree. There is no end to learning. You can't take the time to learn everything or you would never get started.

So a better question might be "How much do you learn before you get started?"
AT the very minimum you are going to need to know how to load your IDE of choice (assuming you use an IDE) and install the JDK.

One extreme, the one I lean towards, would be to jump in with both feet. I find it is much easier to learn a new computer language by writing code in that language. When I get stuck I go look at the tutorials or something. They say we learn best by our mistakes. So I make a lot of little mistakes.

print("hello world"); // doesn't work
println("hello world"); // still doesn't work.
cout.println("hello world"); // nope
<search tutorial>
System.out.println("Hello World!"); // success

That is three mistakes right there, I am learning fast.

But I may not be representative. You might benefit from at least reading through the first of the Java Tutorials offered by Oracle. That would get you a feel for how to do some basic things quickly. It will also give you a flavor of what you can do with simple Java. It will set your expectations reasonably and wet your appetite for more. How many of those tutorials should you complete before you get started? Well, personally, I can't stand to do any of them. I would say read through them, and when you get antsy to try something you just saw, then jump in.

The other extreme is to try and learn as much as you can so you don't make mistakes, (or at least you know where to go to find the answers you need). I learn more about java all the time, even though I have already written much code. I think that is normal. What's more, I find that as I study other languages, I learn still more about Java because it shows me more clearly what Java does well, and what it doesn't. But of course you can't be bothered to learn every language before you start writing programs in your first language. That would be the other extreme from the one I chose. AS I said at the beginning, it is all a matter of degree.


4 years ago

Rob Spoor wrote:In other words, they couldn't do either.

Absolutely. They can't do either of them now. But if they had done them at the time they implemented the wrapper classes, then they could have done this. Sadly, until they implemented autoboxing the value of this would not have been apparent.

Winston Gutkowski wrote:And isn't it interesting that offering something as "simple" as autoboxing...is fraught with so many difficulties?

Oh man that is so true. So very, very true.
4 years ago
Hello everyone.
I have a parent class that specifies methods that utilize fields to return results. The goal is to have the fields be instantiated by child classes, but I need to be SURE they are instantiated or I could get a null pointer exception. Because sometimes the fields refer to heavy weight objects, I do not want the fields instantiated by the parent's constructor and then immediately replaced by the child's constructor. I want to make sure that every such variable is definitively initialized. Ideally I would like them to be final.

So to make this concrete lets say we are making some message parsing classes for different kinds of TCP/IP messages. For example: eMail (SMTP), time(NTP), web (HTTP), etc.



And so now we can see the problems. First, my parent class, AbstractMessageParser did not have a constructor. That means I cannot make the fields final, even though for any given parser, they may never change. That is annoying if I want to make the Parser classes immutable for some reason. So I decide to add a constructor that takes the values of these two fields as arguments. I then force child classes to pass these values to their super constructor. Even if I didn't care about finality, it is critical that all the fields used by the methods defined in the parent class are instantiated in the constructors of the child classes. I have no way to enforces this (that I know of) without the constructor.

So we have now have


This has 2 problems.
(1) a network message might have far more than 2 parameters that define it. There could many common parameters, and the constructors would get tedious. A builder pattern is the obvious solution to this problem.
(2) the call to super() in the child class, must be the first line in the constructor, but some fields that I have to pass may not have a simple construction and could not be easily built in the parameter field of the call to super. You could fix this by making the Smtp Constructor private and adding a public static factory method to the class.

You will forgive me if I forgo writing out the code possible code for the builder and the factory method patterns. As an alternative to the builder method in item #1, I could also create a set of parallel container classes (by 'container class I mean a class that has no methods) to hold the constants associated with a particular type of message. Since most of those constants would be immutable, this system would be advantageous if many instances of the parser were required. But it even more code that needs to be written for what I feel should be a rather simple problem.

So what I _want_ to be able to do is something like the following.

I want to declare all the common fields in the parent class (AbstractMessageParser),
I want to declare them to be final, but not initialize them.
I want to be forced by the compiler to initialize the final fields in the constructor of all child classes or be forced to declare the child class abstract.


Now things are much easier to write. I have one parent class that declares the common state, and a number of child classes, each of which has a host of constants that are specific to its own class, that implement that state. NO builder pattern, no parallel classes, no factory methods. Piece of cake. But it doesn't work.

Is there some way to do this sort of thing with annotations? And/or some kind of testing paradigm?

Perhaps I could put the @Override annotation on the fields, and if they hide a field in the parent class (same name and same type) then the field of the parent class would not be initialized. The point about not being initialized is important, because if the field declares an object that takes a lot of time to construct you don't want to instantiate it twice. And you certainly don't want a hidden instance of a field that you don't use taking up space (as if hidden fields weren't dangerous enough).

It really feels like there should be something for this situation. Some keyword or usage of Java syntax that I haven't learned yet. Can someone set me straight?






4 years ago

Campbell Ritchie wrote:Bloch (loc cit) gives an example where the behaviour of < > and == on an Integer object gives unexpected and incorrect results.

Rob Spoor wrote:If you compare a primitive with an object, the object is always unboxed. That can lead to some surprising NullPointerExceptions.

Perhaps more syntactic sugar should have been made to address this at the time of release. For example, they could have made it an error to create an instance of [Number] that was null. They could have overloaded == when 2 boxed types were involved. But maybe that was impossible for other reasons I haven't considered.

but the fact is that I don't know ... and I don't really want to have to know either


In my own code, I might make an explicit cast on the object. The cast makes it clear what the original programmer intended, and it is a nice "heads up" to whomever reads your code 3 years from now that some variables are not primitives. As Rob pointed out, there is an implicit cast, but the advantages of making it explicit outweigh the 5 keystrokes of "(int)".
4 years ago
I am not quite so pessimistic as the others.

Even if Java is your first language, if you work at it regularly with some modest instruction then it won't be long before you are creating projects that are hundreds of lines long. Writing these things is a fairly low hurdle and if you are doing it only in your spare time you might be there in a few hundred hours of work. But just making them or understanding them should not be your goal. There is more to programming than that (my opinion).

I would say that you need to break your "gaining control of programming" into individual parts that you master in parallel.

1) the Syntax (e.g Java is a strongly typed language with C-like syntax and classes)
2) Language peculiarities (For example: implements generics by erasure, doesn't support multiple inheritance, uses primitives as well as boxed types, early java didn't have enum at all, modern enum "constants" are full blown classes)
3) the "standard" libraries (that come with the JDK)
4) interlanguage commonalities (design patterns, thread safety, testing strategies, documentation habits, agile development)
5) Black Magic (learning how API's evolve over time, how your own code might change later)


So with this framework, I want to try to answer your question. If you want to write a stack or some simple recursion, then you can probably do that with just #1 and #2. That is all you need to write a LOT of great programs in Java. But if your program must work under heavy load, be scalable to multiple processors, and takes 3000 lines of implementation, then you are going to need some of #4, and you will make your load lighter if you know some of #3. Finally, if you are going to write programs that write programs, or write optimized compilers for a scripting language, then I think you need some of that #5.

when you see a really large set of code that someone else wrote and you can figure the code in a glimsp.

I have spent about half of my career doing this. I have learned that it usually has more to do with the skill of the person that wrote the code than your own. Some people write easy to follow code with documentation to help you through the rough parts. Others write spaghetti code that is really hard to figure out. I call this latter group the KIA programmers.

Your stated goal was to be good enough to say "Yeah, I can do that" on just about any project. Lots of programmers get to that point and just stop. But I would say that there is a lot more to computer programming than that just that. There is a lot of things you need to know before I look at you code and say "this guy is certainly not a KIA".




4 years ago

Campbell Ritchie wrote:No, that is not mutability. This is what mutability would look like:-

Yeah, you are right. I was thinking about that on the way home. YOurs is a much better example of what mutability look like. No one would expect my assert to pass.

I don't think anything about that design principle, since I created it.

I choose my wording very carefully. Your introduction to that design principle was a bit vague. You said "I think we end up going back to the earlier post with the quotes from Bloch's book. Maybe we need a new design principle" That sounded to me as if you might have been attributing those words to Bloch, and also possibly some earlier post. I couldn't find such a quote in his book, but didn't look very hard. . I think your principle is valid, but it doesn't say much outside the context of this discussion. For instance, it doesn't say anything about using (or not using) boxed types at any other time. What I am looking for is a design principle that tells me (and other programmers) how to design new API's.

From this discussion it really seems like the boxed types are really only a problem in 2 circumstances.
1) Where you need mutability to avoid creating thousands of short lived instances.
2) Where just going through the process of dereferencing the value could affect performance.

If you do not engage in premature optimisation, then you probably shouldn't be worried about either of these. And if compilers were smart enough to recognize this issue, then they should able to compile this out anyway as long as primitives are a part of the JVM. Which leads me to this kind of rule.

Use boxed types for all variables EXCEPT where performance requires that you use primitives.

That said, I have since looked at some more APIs (including the Guava libraries) and it is almost a universal practice to build API's with primitves. Indeed, within the implementation code I saw, most programmers seem to use the following rule.

use primitives for all variables EXCEPT where they must interact with generic types.

. My first rule looks good on paper, but even I wouldn't advocate it given the overwhelming precedent to the contrary.




4 years ago

Campbell Ritchie wrote:I think we end up going back to the earlier post with the quotes from Bloch's book. Maybe we need a new design principle

Always use primitives for arithmetic, not boxed objects.

This was exactly the conversation I wanted to read. A bunch of experts talking about the ramifications of using boxed vs primitive types. I feel humbled. Truly.

Cambell, do you think that design rule implies that all other activities should be done with boxed types?

Some comments on what other have said....
Something like Boolean has only 3 states (including null) and the OS should more or less never use more space than that. And you don't do arithmetic with them, only boolean logic and that can be done equally well with Boolean.TRUE and Boolean.FALSE as with booleans I would think. This seems like a pretty clear case where the compiler could make a boxed type every bit as flexible as a primitive.

As for Integers, I can see how that would pile up short lived instances of small classes if used as a counting variable in a long loop.

Campbell Ritchie wrote:Bloch's example took 1.7s with longs and 14s with Longs when I tried it a few seconds ago.


But I am working hard to avoid thinking about those kinds of performance issues. It is rough for me because I come from a background in embedded programming where those kinds of issues were paramount! Most of the time you are NOT in loops. When ExecutorService returns the number of active threads it is returning a number that is almost certainly less than 1000, and it is highly unlikely that the caller would be looping on that result anyway. And so what if he did? Is it unfair to make caller responsible for unboxing the result for performance reasons if, and only if, that was necessary in his environment and/or his application?


Better still, wouldn't be reasonable for the programmer to expect that the compiler to take the liberty of converting an Integer to an int in a loop? After all, it can take the liberty of promoting things out of the loop and making other structural changes if it can be sure it will not affect the result (within the confines of a single thread). If the compilers make the move first, it should not hurt existing code. Perhaps that is what Jesper meant when he said

Jesper de Jong wrote:The idea is to remove primitives from the Java programming language, but not from the JVM.



Campbell Ritchie, quoting J. Bloch wrote:... the == operator does not operate on intValue() (for Integers) or similar but looks for reference identity.
Also Bloch says you can't use default values; the default value for an Integer field is null, so any attempt to unbox that will cause a NullPointerException.

This would suggest that more syntactic sugar is needed. So if ++myInteger works, and I think someone suggested that += and *= also work, then why now allow "==" on Integer to compare the values of the Integer? I realize that means you have just overloaded the == operator, but if you can overload the others, why not this? Well the could possibly a problem where you REALLY wanted to compare if two instances of Integer were really the same instance, but in that rare circumstance it would have been sufficient to cast one or the other to Object before doing the compare. But I haven't thought this through, maybe there is some huge problem with that idea. There would probably be objections if we tried to do it now!

Winston Gutkowski wrote:I just don't like the fact that they've changed a supposedly immutable object into a "mutable" one. And it's done silently.

Why? Didn't we do the same with String? Specifically I can write
Line 5 sure makes it look like String a is mutable. We have already broken the rules in an effort to make String immutable. For starters we overloaded the + operator! Maybe they could have done the same with Integers and given them the same type of special handling given to String (a courtesy to the programmer). But it might be hard to do it now after the fact.


but not arithmetic or anything that involves boxing AND unboxing in the same "operation"

Perhaps there should indeed be a warning about that, just like the warning you get when comparing String with ==.
4 years ago

How can I improve the code?


Improved? What aspect of your program does not meet your satisfaction?
Does it not work as you expect? Does it fail to compile at a certain line? If so which one?
I am trying to help you, but I don't know what you need


Could I ask you to please rephrase your question. While you are at it, please repost your code but surround it with the Code tags. To do that, copy and paste your code as you did before, then select it in the editor and click the "Code" button.

The advantages of that are 2 fold. First, all your code formatting will remain visible. Second, it adds line numbers so that we can say something like "In line xx, you need to....".
4 years ago
Thanks Fred for the link.
Thanks Bear for pointing me in the correct direction.
4 years ago