Reformatted the code and added some traits to avoid code duplication