Skip to content

Instantly share code, notes, and snippets.

@yoavst
Last active December 20, 2021 13:09
Show Gist options
  • Select an option

  • Save yoavst/32a51fc9717f53fcc9a92261bb116a9c to your computer and use it in GitHub Desktop.

Select an option

Save yoavst/32a51fc9717f53fcc9a92261bb116a9c to your computer and use it in GitHub Desktop.

Revisions

  1. yoavst revised this gist Dec 20, 2021. 1 changed file with 1 addition and 1 deletion.
    2 changes: 1 addition & 1 deletion readme.md
    Original file line number Diff line number Diff line change
    @@ -92,7 +92,7 @@ B b = new B();
    b.f(); // "B", the compiler thinks `b` is `B`, and B::f exists, so it is called
    (A b).f(); // "A", the compiler thinks `b` is `A`, and A::f exists, so it is called
    b.g(); // "B", since `g` implemented in `B`, and B::f hides A::f - static dispatch
    (A b).g(); // "A", since `g` implemented in `A`, and the compilers thinks we are `A` - static dispatch
    (A b).g(); // "B", since `g` implemented in `B`, and the compilers thinks we are `B` - static dispatch
    ```

    [1] Actually more, but most of them are specialized version of those 2. Another one is for dynamic typing capability of the JVM.
  2. yoavst revised this gist Dec 19, 2021. 1 changed file with 1 addition and 1 deletion.
    2 changes: 1 addition & 1 deletion readme.md
    Original file line number Diff line number Diff line change
    @@ -13,7 +13,7 @@ In java we have 2 concept of calling methods[1]:
    ## Hiding vs Overriding
    Hiding means that **in some scopes**, `the new f` will be called instead of `f`. Note that it depends on the scope. It only happens where *Static dispatching* is used:

    * (staitc?) fields
    * (static?) fields
    * *static* methods
    * private methods.

  3. yoavst revised this gist Dec 19, 2021. 1 changed file with 1 addition and 1 deletion.
    2 changes: 1 addition & 1 deletion readme.md
    Original file line number Diff line number Diff line change
    @@ -11,7 +11,7 @@ In java we have 2 concept of calling methods[1]:


    ## Hiding vs Overriding
    Hidding means that **in some scopes**, `the new f` will be called instead of `f`. Note that it depends on the scope. It only happens where *Static dispatching* is used:
    Hiding means that **in some scopes**, `the new f` will be called instead of `f`. Note that it depends on the scope. It only happens where *Static dispatching* is used:

    * (staitc?) fields
    * *static* methods
  4. yoavst revised this gist Dec 19, 2021. 1 changed file with 1 addition and 1 deletion.
    2 changes: 1 addition & 1 deletion readme.md
    Original file line number Diff line number Diff line change
    @@ -1,6 +1,6 @@
    Java Cheatsheet
    ===============
    General conectps you've got to understand so everything could possibly make sense to you.
    General concepts you've got to understand so everything could possibly make sense to you.

    ## How a method is called
    In java we have 2 concept of calling methods[1]:
  5. yoavst revised this gist Feb 1, 2020. 1 changed file with 29 additions and 1 deletion.
    30 changes: 29 additions & 1 deletion readme.md
    Original file line number Diff line number Diff line change
    @@ -132,4 +132,32 @@ b.g(); // "B", call A::g (since B doesn't override), but A::f is virtual, and t
    ## Fields
    Fields are accessed using static dispatch, therefore they work exactly like static methods.

    ```java
    ```java
    class A {
    String f = "A";

    void g() {
    System.out.println(f);
    }

    void h() {
    System.out.println(f);
    }
    }

    class B {
    String f = "B";

    @Override
    void g() {
    System.out.println(f);
    }
    }


    B b = new B();
    b.g(); // "B", `B::g` is called, and B::f hides A::f.
    (A b).g(); // "`B::g` is called
    b.h(); // "A", `A::h` is called, and the compiler static dispatch fields, so since the static type is A, the compiler only knows about A::f.
    (A b).h(); // "A", "`A::h` is called
    ```
  6. yoavst created this gist Feb 1, 2020.
    135 changes: 135 additions & 0 deletions readme.md
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,135 @@
    Java Cheatsheet
    ===============
    General conectps you've got to understand so everything could possibly make sense to you.

    ## How a method is called
    In java we have 2 concept of calling methods[1]:

    * Static dispatching - The Java compiler knows in **compile time** which function code block to call

    * Dynamic dispatching - The Java compilers inserts a code, that on **runtime** decides which function code block to call


    ## Hiding vs Overriding
    Hidding means that **in some scopes**, `the new f` will be called instead of `f`. Note that it depends on the scope. It only happens where *Static dispatching* is used:

    * (staitc?) fields
    * *static* methods
    * private methods.

    Overriding, on the other hand, means that **every time** that you call `f`, `the new f` will be called instead. Therefore, it only happens where *Dynamic dispatching* is used:
    * constructors
    * class non-private methods


    ## runtime type vs "static" type
    Every instance has a runtime type. The type is `T` in `new T(...)`. This is the real type of the instance which influences the *Dynamic dispatching*.

    However, since we are doing OOP, we can treat an instance as an upper type (for example, one can treat `String` as `Object`). Therefore, every expression in Java has a "static" type, the type that the Java compiler is sure the expression is of. Note that the static type of expression depends on the scope. The static type influence the `static dispatching`

    Given an instance `x` of (runtime) type `X extends\implements T` with static type `T`, you can only call methods/access fields defined on `T`, since the compiler only knows about them as it treats `x` as instance of `T`.

    ## Lookup order
    Given a symbol `s` we want to access/call, the lookup order is:
    * In method scope
    * static class scope
    * class scope
    * static parent class scope
    ...
    * static `Object` scope
    * `Object` scope
    * "imported" scope

    **Note:** It's OK to have a (static?) method and a (static?) field with the same name (since you can't do: `field(...)` or `::field`)

    ## instance initialization order:
    1. arguments are evaluted
    2. If this constructor call another constructor, evaluate the arguments and call the other constructor (go back to 2)
    3. Call super constructor
    4. execute class initializers (`{}` in class body) and evaluate instance variable initializers `String x = ...` from top to bottom.
    6. execute the rest of the method body

    On exception stop the initialization and throw the error

    ## Methods

    Say `C extends B extends A` and we have an instance `C c`:

    * inside a method body in `B` (meaning: inside `class B { ... }`) the static type of `c` is `B` - Inside `T` the compiler thinks that you are `T`.

    ### Static methods

    Fun facts:
    * You **can** call a static method on an instance: `a.staticMethod()`
    * You **can't** have a static and non-static method with the same signture.

    **Why?** Given `A a` with `static void f()` and `void f()`, what does `a.f()` mean?


    Static methods are static dispatched. Therefore, they are affected by hidding:
    ```java
    class A {
    static void f() { System.out.println("A"); }

    void g() {
    f();
    }
    }

    class B {
    static void f() { System.out.println("B"); }

    @Override
    void g() {
    f();
    }
    }


    B.f(); // "B"
    A.f(); // "A"
    B b = new B();
    b.f(); // "B", the compiler thinks `b` is `B`, and B::f exists, so it is called
    (A b).f(); // "A", the compiler thinks `b` is `A`, and A::f exists, so it is called
    b.g(); // "B", since `g` implemented in `B`, and B::f hides A::f - static dispatch
    (A b).g(); // "A", since `g` implemented in `A`, and the compilers thinks we are `A` - static dispatch
    ```

    [1] Actually more, but most of them are specialized version of those 2. Another one is for dynamic typing capability of the JVM.

    ### virtual Methods
    Virtual methods (non-private methods) are called using dynamic dispatch, therefore are subject to overriding concept.

    * The annotation `@Override` is completely optional. However, if it is used, the compiler throw compilation error if used incorrectly.

    ```java
    class A {
    void a() { System.out.println("A"); }

    void f() { a(); }

    void g() {
    f();
    }
    }

    class B {
    void b() { System.out.println("B"); }

    void f() { b(); } // overrides A::f, not hidding!!!

    }


    B b = new B();
    b.f(); // "B", since dynamic type is B, call B::f, which calls b, which prints "B"
    (A b).f(); // // "B", since dynamic type is still B
    b.g(); // "B", call A::g (since B doesn't override), but A::f is virtual, and the dynamic type is B, so it calls B::f which prints "B"
    (A b).g(); // "B", Same as above
    ```


    ## Fields
    Fields are accessed using static dispatch, therefore they work exactly like static methods.

    ```java