Ручная компиляция исходного кода java

Разберемся, как в ручную откомпилировать программу. 
Допустим, имеется следующая структура папок: 
src -> ru -> golov -> main -> Main.java, 
src -> ru -> golov -> io -> Printer.java
classes -> .
Файл Main.java:
package ru.golov.main;

import ru.golov.io.*;

public class Main {
    public static void main(String[] args) {
        Printer printer = new Printer();
        printer.print("Hello world!");
    }
}

Файл Printer.java:

package ru.golov.io;

public class Printer {
    public void print(String s) {
        System.out.println(s);
    }
}
Выходим в корневой каталог, компилируем программу: javac -d classes -cp src src/ru/golov/main/Main.java classpath указывается для того, чтобы компилятор понимал, относительно какой директории делаются импорты. Флаг -d говорит о том, что скомпилированные class - файлы должны быть расположены в дирректории classes.
Для того, чтобы запустить программу:
java -cp ./classes ru.golov.main.Main

Function closures

    Good day! Recently, I studied JavaScript and сame across an interesting topic: function closures. This feature available in many functional programming languages, but I would like to describe it on JavaScript language.
    Let's start! Firstly, we need to get acquainted with the concept of global and local variables.
    In JavaScript, global variables is a variable or function, which are not inside some function. In JavaScript, all global variables are the properties of the global object (for example, in the browser, the global object is window. Example of global variable:
var a = 15;
    The variables, which declared inside the function are called local. Every function has own special object, which contains all variables of function - LexicalEnvironment object. When we create new function, we create new LexicalEnvironment object also. Moreover, every LexicalEnvironment object has a property [[Scope]], which contains a reference to an outer object LexicalEnvironment. As result, if we can't find a variable in the current LexicalEnvironment, we can find it in the outer LexicalEnvironment object. Let's review the example:
function outerFunc() {
  var a = 5; //LexicalEnvironment = {..., a: 5};

  (function innerFunction() {
    //LexicalEnvironment of inner function not contains "a" variable
    //Take the variable from outer LexicalEnvironment 
    console.log(a);
  })();
}

outerFunc(); //Output - 5;
     Now, let's review the definition of closures. According to Wikipedia, "In programming languages, closures (also lexical closures or function closures) are techniques for implementing lexically scoped name binding in languages with first-class functions." AnothrWords, internal function remember the outer LexicalEnvironment and use the variables from there. Let's look at an example and discuss it:
function getCounter() {
  var count = 0;

  return function() {
    return count++; //Usage of outer LexicalEnvironment
  }
}

var counter1 = getCounter();
console.log(counter1()); //0
console.log(counter1()); //1
//...

//Counters are indepentent
var counter2 = getCounter();
console.log(counter2()); //0
console.log(counter2()); //1
    In this example we can see, that inner function use outer variable count and increment it. The result returned by the function call getCounter() refers to it's own outer LexicalEnvironment. When we invoke function getCounter(), we create new LexicalEnvironment and new variable count, as result, all counters are independent.
    I hope, this article gave you knowledge about the concept of closure! If you have a questions, you can ask it in comments.

Design pattern "Strategy"

    Hello everyone! Today I would like to tell you about design pattern strategy. In my opinion, this pattern is very interesting and usefull in day-to-day tasks!

    Strategy is behavioral pattern. It means, that this pattern determinate algorythms and ways to realization of interaction different objects and classes. You can use this pattern, when the behavior of your program depends on the situation. For example, you have several ways to implement some feature and your choice depends on the situation - it's a good reason to use strategy pattern!

    Now, let's review the components of this pattern. I would like to show all examples in the java language, but I try to describe it, if you are not familiar with it.
  1. interface Strategey - interface, contains only one method - execute(), which execute some action;
  2. class Context - class, contains some Strategy, which you can change depends on the situation, and method, which execute some strategy;
  3. set of classes, which implements Strategy (ConcreteStrategy) - realizations of interface Strategy, or, in other words, the set of classes, which determ the behavior of program.
    Now, I would like to show you example of the using this pattern. Imagine, that we would like to write compressor, but there are many methods to compress file (for example RAR, ZIP etc), and we whant to use different methods depends on the situation. Let's rewiev the code:

public interface Strategy {
    void execute(File file);
}
public class Context {
    private Strategy strategy;

    public void setStrategy(Strategy strategy) {
        this.strategy = strategy;
    }

    public void execute(File file) {
        strategy.execute(file);
    }
}
public class RarCompressionStrategy implements Strategy{
    @Override
    public void execute(File file) {
        // There should be rar-compression algorithm
    }
}
public class ZipCompressionStrategy implements Strategy {
    @Override
    public void execute(File file) {
        // There should be zip-compression algorithm
    }
}
public class Main {
    public static void main(String[] args) throws IOException {

        //Creating the context object
        Context context = new Context();

        // Give the user the choice of algorithm.
        BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
        System.out.println("Please, select the compression algorithm");
        String answer = reader.readLine();

        if (answer.toLowerCase().equals("rar")) {
            context.setStrategy(new RarCompressionStrategy());
        } else if (answer.toLowerCase().equals("zip")) {
            context.setStrategy(new ZipCompressionStrategy());
        } else {
            // if the user entered incorrect data
            throw new IllegalArgumentException();
        }

        //Executing some strategy
        context.execute(new File("some file"));
    }
}

    In this case, user chose the method of compressing. I hope, this example was interesting for you!

Welcome!


   Hello everyone! Recently, the idea came to me create my own blog, where I can share my thoughts about programming, give some advices or discribe some interesting for me topics.

    The aim of my blog – simplify and make complex topics easy-understanding for everyone! I will try to write new articles regular and stably. There are the topics that will be considered in the near future:

  • Advises for beginner – programmers;
  • Functional programming;
  • Django for beginners;
  • Design patterns in examples;
  • Review of interesting programmers educational projects.

    I think, my articles will be interesting for you! See you soon!