I have been coding in python for a couple months now, and something has always been on my mind. I know you can have classes in your .py file, but you don't have to. My question is, is it good practice to always have your code in a class, or is it not necessary?
FYI: I have been coding in Java for a few years, so I'm used to always having a "main" class and a main method that runs everything.
It depends on what your file is. In theory everything (saying this with some hesitation) can be written as a class. But it is a bit overkill to do that just for the sake of being "correct" and will probably make your code look strange rather than clear. In general i would make the following distinctions between cases
If it is the source for a big project which makes sense to be organized in an object oriented fashion, then you would have a class which defines exactly that. This is great because then you can inherit the class for variants or child projects.
If you are creating a list of utility functions to use for all your projects, such as array manipulations or little tools that are always handy, then a function-only file is the way to go
If you are writing a script which is designed in order to execute a specific task in the way a script would, then i would define task-specific source in a .py file and include the code related to the execution under the statement
if name == 'main':
Related
So I have a Java application I will be releasing to one of my communities for a price. The app is just about complete and ready to be obfuscated but the problem is;
I found that when I add the Jar to another project in Eclipse you can instantiate classes externally and use my program as an external library to make scripts outside of my program. This is not what I'm wanting to achieve here... I'm self taught so I have grey areas of knowledge as I haven't learned formally, but I'm pretty experienced in Java still... I've tried googling it and nothings coming up, maybe I'm not phrasing it correctly. But if I could get some help it would be appreciated.
Here is my structure of my packages:
src.com
Contains main class
src.com.scripts
Contains Abstract Script class
src.com.scripts.impl
Contains the actual scripts that extend the abstract Script class
What I've tried doing:
I removed the public Identifier from the Abstract Script class but then it isn't visible to the main class to call it from as it is in the package before. So how can I go about this when my project is sorted in packages and they all need to access eachother?
There is no solution.
If people want to reverse engineer your code, they will. There is nothing you can do to change that. public/private are essentially meaningless beyond helping you write good portable code.
That being said, Java is generally much easier to reverse engineer and make bindings to than other languages. Java doesn't inline functions and unless told otherwise, it will even leave all of your class and method names intact. If you had used a language like C, the optimized binary would be a bigger pain to work with, but the result would still be the same.
Just obfuscate the jar and call it a day. Manually changing how you write your code is more harmful to you than it is to them.
It might sound a little bit weird, but I am looking for a possibility to test if some statements in the code are rejected by the typechecker (which means that the code should NOT compile).
Be explain my intend: I am running a controlled experiment on type-systems where my subjects have to write some methods in java for me. The functionality of the methods written by the subjects can be easily tested using unit-tests, but I also want the methods to be well-typed (which means that some methodcalls should not be allowed).
One way I could imagine to achieve that would be writing the statements which should break the build into a seperate file, add it to the classpath and run javac to see if any error occurs during the build. Although this might work, it does not feel very sophisticated, so my question is: Is there any better way to (automatically) test if some statements are refected by the typechecker?
This is a variation of the Halting Problem, which isn't solvable in the general case. To do this, you have to run (or in this case compile) the code. Therefore, the solution you've already proposed is the best solution.
Have you looked at the Checker Framework? It can be used to static code analysis and more. It might be a good fit for what's you are doing. Here is the link on my answer with an example of the annotation type processor.
Also you may find the Java Compiler API quite helpful. It allows to execute javac programmatically in a single java machine. So you could use it as a part of your tests.
(This question is related to any kind of development, not only games).
I am relatively new to game development with Java.
I made a number of games, and started noticing that at the beginning of each project, I pretty much always rewrite very similar code and classes.
For example: The structure of the game loop, the base class for all game entities, the mechanism for getting keyboard input and moving the character accordingly, etc. All of these are very similar (but not identical) from project to project.
I realized that the best way to deal with this, is probably to create a library which will store all of this code that I constantly have to rewrite.
The problem is, I don't really know where to start.
A library is a JAR that contains a collection of classes (is this accurate?). If so, than I can't just create a BaseGameEntity class and put it in a library to use in my games.
This is because because this class is very similar from game to game I make, but not identical. I still always need to change some of it's code. So I can't have it locked up in a library.
Same thing goes for the mechanism for getting input from the keyboard to move character. I could encapsulate it in a class and put it in a library, but again - it's never identical from game to game. I still need to adjust it's code, I can't just reuse the exact same code.
What is the common solution for this? Are there common 'strategies' used for these (I assume) common cases? Or do developers use their common sense and known design patterns to achieve this, without any specific 'strategy'?
EDIT: Are there common design patterns I should learn to help me build a good reusable library?
I would recommend if you're doing any type of development in Java that you learn some design patterns. Books I find are ineffectual for non-academic programmers (i.e. those that didn't get a Computer Science degree) so your best bet is to go to the web. Here is a link to a page I still use:
http://www.fluffycat.com/Java-Design-Patterns/
Basically the problems you are facing now have already been solved, albeit in a general way, and there is a collection of those solutions somewhere. Your challenge is to identify the problem you are trying to solve in your own code, and then choose the pattern that best solves your problem. This requires being more than just nominally familiar with the patterns.
Sometimes looking at things like design patterns when you're new to programming can be daunting, so a solution in the interim for you would be to (a must-do practice in programming anyway) take common functionality in your code and break it down into separate, well-defined classes (look up OOP cohesion). For instance, if a class you've written has a method that takes a String and formats it a certain way, you might want to create a new class that just does that via a public static method, rather than keep that single purpose code inside your original class. Same thing goes with, say, a method that reads data from a properties file, or a method that deals with time, etc. This would be the first step to creating a package or starting framework that you can reuse. The goal is that if you break your code into pieces small enough, they can be used anywhere.
You have two choices:
1- Refactor your code so that you can put some never changing pieces into a library and extract to a JAR.
2- If you can definitely not extract to a JAR because your code will always change a tiny bit, then simply create a separate Java project with the code that would ideally go in a library but that can't because of its tiny differences from game to game, and then reference the project adding it to the build path of your actual game project. Then when the next game comes around, make a copy of your original "library" project and repeat.
I am learning the concepts of Test-Driven Development through reading the Craftsman articles (click Craftsman under By Topic) recommended in an answer to my previous question, "Sample project for learning JUnit and proper software engineering". I love it so far!
But now I want to sit down and try it myself. I have a question that I hope will need only a simple answer.
How do you organize your JUnit test classes and your actual code? I'm talking mainly about the package structure, but any other concepts of note would be helpful too.
Do you put test classes in org.myname.project.test.* and normal code in org.myname.project.*? Do you put the test classes right alongside the normal classes? Do you prefer to prefix the class names with Test rather than suffix them?
I know this seems like the kind of thing I shouldn't worry about so soon, but I am a very organization-centric person. I'm almost the kind of person that spends more time figuring out methods to keep track of what to get done, rather than actually getting things done.
And I have a project that is currently neatly divided up into packages, but the project became a mess. Instead of trying to refactor everything and write tests, I want to start fresh, tests first and all. But first I need to know where my tests go.
edit: I totally forgot about Maven, but it seems a majority of you are using it! In the past I had a specific use case where Maven completely broke down on me but Ant gave me the flexibility I needed, so I ended up attached to Ant, but I'm thinking maybe I was just taking the wrong approach. I think I'll give Maven another try because it sounds like it will go well with test-driven development.
I prefer putting the test classes into the same package as the project classes they test, but in a different physical directory, like:
myproject/src/com/foo/Bar.java
myproject/test/com/foo/BarTest.java
In a Maven project it would look like this:
myproject/src/main/java/com/foo/Bar.java
myproject/src/test/java/com/foo/BarTest.java
The main point in this is that my test classes can access (and test!) package-scope classes and members.
As the above example shows, my test classes have the name of the tested class plus Test as a suffix. This helps finding them quickly - it's not very funny to try searching among a couple of hundred test classes, each of whose name starts with Test...
Update inspired by #Ricket's comment: this way test classes (typically) show up right after their tested buddy in a project-wise alphabetic listing of class names. (Funny that I am benefiting from this day by day, without having consciously realized how...)
Update2: A lot of developers (including myself) like Maven, but there seems to be at least as many who don't. IMHO it is very useful for "mainstream" Java projects (I would put about 90% of projects into this category... but the other 10% is still a sizeable minority). It is easy to use if one can accept the Maven conventions; however if not, it makes life a miserable struggle. Maven seems to be difficult to comprehend for many people socialized on Ant, as it apparently requires a very different way of thinking. (Myself, having never used Ant, can't compare the two.) One thing is for sure: it makes unit (and integration) testing a natural, first-class step in the process, which helps developers adopt this essential practice.
I put my test classes in the same package as what they are testing but in a different source folder or project. Organizing my test code in this fashion allows me to easily compile and package it separately so that production jar files do not contain test code. It also allows the test code to access package private fields and methods.
I use Maven. The structure that Maven promotes is:-
src/main/java/org/myname/project/MyClass.java
src/test/java/org/myname/project/TestMyClass.java
i.e. a test class with Test prepended to the name of the class under test is in a parallel directory structure to the main test.
One advantage of having the test classes in the same package (not necessarily directory though) is you can leverage package-scope methods to inspect or inject mock test objects.
This is for an Android application but I'm broadening the question to Java as I don't know how this is usually implemented.
Assuming you have a project that targets a specific SDK version. A new release of the SDK is backward incompatible and requires changing three lines in one class.
How is this managed in Java without duplicating any code(or by duplicating the least amount)?
I don't want to create two projects for only 3 lines that are different.
What I'm trying to achieve in the end is a single executable that'll work for both versions. In C/C++, you'd have a #define based on the version. How do I achieve the same thing in Java?
Edit: after reading the comments about the #define, I realized there were two issues I was merging into one:
So first issue is, how do I not
duplicate code ? What construct is there that is the equivalent of a
#define in C.
The second one is: is it possible
to bundle everything in the same
executable? (this is less of a
concern as the first one).
It depends heavily on the incompatibility. If it is simply behavior, you can check the java.version system property and branch the code accordingly (for three lines, something as simple as an if statement).
If, however, it is a lack of a class or something similar that will throw an error when the class is loaded or when the code gets closer to execution (not necessarily something you can void reasonably by checking before calling), then the solution gets a lot harder. The notion of having a separate version is the cleanest from a code point of view, but it does mean you have to distribute two versions.
Another solution is reflection. Don't reference the class directly, call it via reflection (test for the methods or classes to determine what environment you are currently running in and execute the methods). This is probably the "official" approach in that reflection exists to deal with classes that you don't have or don't know you will have at compile time. It is just being applied to libraries within the JDK. It gets very ugly very fast, however. For three lines of code, it's ok, but doing anything extensive is going to get bad.
The last thing I can think of is to write common denominator code - that is code that gets the job done in both, finding another way to do it that doesn't trigger the problematic class or method.
I would isolate the code that needs to be different in a separate class (or multiple classes if necessary), and include / exclude them when building the project for the different versions.
So i would have like src/java/org/myproj/Foo.java which is the common stuff, and then oldversion/java/org/myproj/Bar.java and newversion/java/org/myproj/Bar.java which is the different implementations of the class that uses changed api.
Then I either compile "src/java and oldversion/java" or "src/java and newversion/java".
Possibly a similar situation, I had a method which wasn't available in the previous version of the JDK but if it was there I wanted to call it, I didn't want to force people to use the more recent version though. I used reflection to look for the method, if it was there I called it, if it wasn't I didn't.
Pretty hacky but might give you what you want.
Addressing Java in general, I see two primary approaches.
1). Refactor the specific code to its own library. Have different versions of that library. Effectively your app is creating an abstaction above the different SDKs. Heavyweight for 3 lines of code, but perhaps quite reasonable for larger scale problems.
2). Injection using annotation. Write your own annotation processor to manage the appropriate injection. More work, but maybe more fun.
Separate changing code in different classes with the same interface. Place classes in the same jar. Use factory design pattern to instantiate one or another class depending on SDK version.