How can I enhance my linkedlist implementation in java? I recently implemented Linked List on my own. I did not use generics as I am still learning. How can I improve it:

package datastructures;

class LinkedList
{
    Node head = null; 
    Node tail = null;
    int size = 0;

    public void add(int data)
    {
        Node n = new Node();
        n.setElement(data);
        if(head == null){head = n; tail = n;}
        else
        {
            tail.setNext(n);
            tail = n;
        }
        size++;
    }

    public void size()
    {
        System.out.println("Size of the list is " + size);
    }

    public void addFront(int data)
    {
        Node n = new Node();
        n.setElement(data);

        if(head == null)    {   head = n; tail = n;   }
        else
        {
            n.setNext(head);
            head = n;
        }
        size++;
    }

    public void addLast(int data)
    {
        Node n = new Node();
        n.setElement(data);

        if(head == null){head = n; tail = n;}
        else
        {
            tail.setNext(n);
            tail = n;
        }
        size++;
    }

    public void removeFirst()
    {
        if(size==0){return ;}
        else
        {
            Node n = head.getNext();
            head = n;
        }
        size--;
    }

    public void removeLast()
    {
        if(size==0){return ;}
        else
        {
            Node tmp , prev = null;
            tmp = head;

        while(tmp != null)
        {
            if(tmp.getNext() == tail){prev = tmp;}
            tmp = tmp.getNext();
        }
            tail = prev;
            tail.setNext(null);
        }
        size--;
    }

    public void printList()
    {
        Node cNode = head;
        while(cNode != null)
        {
            System.out.println(cNode.getElement()+" ");
            cNode = cNode.getNext();
        }
        System.out.println("");
    }

    public static void main(String args[])
    {
        LinkedList l = new LinkedList();
        l.add(1);
        l.add(2);
        l.add(3);
        l.add(4);
        l.add(5);
        l.add(6);
        l.add(7);
        l.add(8);
        l.addLast(9);
        l.addFront(0);
        l.printList();

        System.out.println("Head Node is "+l.head.getElement());
        System.out.println("Tail Node is "+l.tail.getElement());
        l.size();

        System.out.println("\\\\\\\\\\\\\\\\Before removing the first element////////");
        System.out.println("");

        System.out.println("\\\\\\\\\\\\\\\\After removing the first element and removing the last element////////");
        System.out.println("");

        l.removeFirst();
        l.removeLast();
        l.printList();
        System.out.println("Head Node is "+l.head.getElement());
        System.out.println("Tail Node is "+l.tail.getElement());
        l.size();
    }

}
class Node
{
    int data;
    Node next;

    public void setElement(int data)
    {
        this.data = data;
    }

    public int getElement()
    {
        return data;
    }

    public Node getNext()
    {
            return next;
    }

    public void setNext(Node n)
    {
        this.next = n;
    }

}
1 Coding conventions

In Java, you should keep the opening curly brace on the same row as the token it relates to. Instead of writing

public void add(int data)
{
    ...
}

...
else 
{
    ...
}


you should write 

public void add(int data) {
    ...
}

...
else {
    ...
}


What comes to other conventions, you should have a single space between if-keyword and the opening parenthesis of the condition. Instead of

if(foo(bar)) ...


you should write 

if (foo(bar)) ...


Also, what comes to the if keyword, you should have another single space between the closing parenthesis of the condition and the opening curly brace. So, instead of 

if (foo(bar)){
    ...
}


you should write 

if (foo(bar)) {
    ...
}


Now, I suggest you do not write more than one statement on a single line. Instead of 

{head = n; tail = n;}


it would be nicer to write

... {
    head = n;
    tail = n;
}


2 Field initializers

The following is superfluous:

Node head = null; 
Node tail = null;
int size = 0;


By default, Java initializes the object fields to null and integer fields to 0. Also, they must be declared private, since otherwise whatever is in your package, it may tamper with the fields. So, you should write 

private Node head;
private Node tail;
private int size;


3 class Node

I think it would be a better idea to declare Node as a private static inner class of LinkedList (see Summa summarum for details). Also, I would rename data to datum since it is the singular form of the word. Also, datum/data may be declared final since it is not modified. Moreover, you could declare both data and next as private and provide appropriate getters and setters.

4 printList

The conventional way to do what you do in printList is to override the Object.toString method returning a string representing the contents of your list.

5 remove*

Your list would be more useful, if your remove* methods returned the datum removed from the list.

6 size()

Printing the current size of the list to standard output is not a good idea. Instead, just return the size and let the caller do whatever (s)he wants with it (for example, print it to console).

Summa summarum

Putting all pieces together, I had this implementation in mind:

package datastructures;

import java.util.NoSuchElementException;

public class LinkedList {

    private Node head;
    private Node tail;
    private int size;

    private static final class Node {

        private final int datum;
        private Node next;

        Node(final int datum) {
            this.datum = datum;
        }

        int getDatum() {
            return datum;
        }

        Node getNext() {
            return next;
        }

        void setNext(Node n) {
            this.next = n;
        }

    }

    public void add(final int datum) {
        Node node = new Node(datum);

        if (head == null) {
            head = node;
        } else {
            tail.setNext(node);
        }

        tail = node;
        size++;
    }

    public int size() {
        return size;
    }

    public void addFirst(int datum) {
        Node node = new Node(datum);

        if (head == null) {
            tail = node;
        } else {
            node.setNext(head);
        }

        head = node;
        size++;
    }

    public void addLast(int datum) {
        add(datum);
    }

    public int removeFirst() {
        if (size == 0) {
            throw new NoSuchElementException("Removing from an empty list.");
        }

        final Node firstNode = head;
        head = head.getNext();
        size--;
        return firstNode.getDatum();
    }

    public int removeLast() {
        if (size == 0) {
            throw new NoSuchElementException("Removing from an empty list.");
        }

        final Node lastNode = tail;
        Node previous = null;
        Node current = head;

        while (current.getNext() != null) {
            previous = current;
            current = current.getNext();
        }

        tail = previous;

        if (tail != null) {
            tail.setNext(null);
        }

        size--;
        return lastNode.getDatum();
    }

    @Override
    public String toString() {
        if (size == 0) {
            return "[]";
        }

        final StringBuilder sb = new StringBuilder("[");
        sb.append(head.getDatum());
        Node node = head.getNext();

        while (node != null) {
            sb.append(", ").append(node.getDatum());
            node = node.getNext();
        }

        return sb.append("]").toString();
    }

    public static void main(String args[]) {
        LinkedList l = new LinkedList();
        l.add(1);
        l.add(2);
        l.add(3);
        l.add(4);
        l.add(5);
        l.add(6);
        l.add(7);
        l.add(8);
        l.addLast(9);
        l.addFirst(0);
        System.out.println(l);

        System.out.println("Head Node is " + l.head.getDatum());
        System.out.println("Tail Node is " + l.tail.getDatum());
        l.size();

        System.out.println("\\\\\\\\\\\\\\\\Before removing the first element////////");
        System.out.println("");

        System.out.println("\\\\\\\\\\\\\\\\After removing the first element and removing the last element////////");
        System.out.println("");

        l.removeFirst();
        l.removeLast();
        System.out.println(l);
        System.out.println("Head Node is " + l.head.getDatum());
        System.out.println("Tail Node is " + l.tail.getDatum());
        l.size();
    }
}


Hope that helps.