int main()
{
    long decimal;
    scanf("%ld", &decimal);
    
    char hexResult[64];
    decimalToHex(decimal, hexResult);
    printf("%s", hexResult);
    
    return 0;
}
string MachineParser::encode(Instruction i)
  // Given a valid instruction, returns a string representing the 32 bit MIPS binary encoding
  // of that instruction.
{
  OpcodeTable* myTable = new OpcodeTable;
  Opcode myOpcode = i.getOpcode();
  string ASMString = "";

   //adds the opcode(alphabetical representation)  of the instruction to the string 
   ASMString += (myTable-> getName(myOpcode) + " ");  // we must find the name for each instruction

  //FOR ITYPE INSTRUCTIONS 
  if(myTable -> getInstType(myOpcode) == ITYPE)
  {


  if(myTable -> IMMposition(myOpcode) == 1)  //symbolizes a load store instruction since immediate is
    //is at position 1 
    {
      if( myTable -> RTposition(myOpcode) != -1)      //if the RT register is being used 
      {
        ASMString += i.getRT();
        ASMString += ", "; 
      }
      //convert the immediate to a string, the method deals with the two's complement conversion
      ASMString+= decimalToString(i.getImmediate());

      if( myTable -> RSposition(myOpcode) != -1)
      {
        ASMString += "("+i.getRS()+")"; //paranthesis for load instruction $register(offset)
      }
    }
  else
    //THIS IS FOR INSTRUCTIONS THAT ARE NOT LOAD OR STORE 
    {

    if( myTable -> RSposition(myOpcode) >= 0)
      {
        ASMString += (i.getRS());
        ASMString += ", "; 
      }
      if( myTable -> RTposition(myOpcode) >= 0)
      {
        ASMString += i.getRT() ;
        ASMString += ", "; 
      }
      
    if((ASMString.find("beq")!=std::string::npos)) //meaning instruction is of type branch if equal to thus immediate is an addresss
    {
      ASMString += decimalToHex(i.getImmediate());  //converts the address to which we have to branch from decimal to hexadecimal
    }
    
    else  //if its not a beq instruction then the immedaite is not an address so we simply parse it to a string 
          //instead of treating it as an address 
    {
      ASMString += decimalToString(i.getImmediate());
    }
  }
}

  //FOR RTYPE INSTRUCTIONS 
else if(myTable -> getInstType(myOpcode) == RTYPE)
  {
  
//I've put a series of conditional statements which using the opcode type to determine the fields that need to be added to 
// ASM String 
//we iterate through the number of elements in an instruction of type (myOpcode) and 
//we find the RD, RS, RT as well as the immediate  
      for(int position = 0; position < myTable -> numOperands(myOpcode); position++)
    {
      if((myTable->RDposition(myOpcode)) == position)
      {
        ASMString += (i.getRD());
      }
      if(myTable-> IMMposition(myOpcode) == position)
      {
        ASMString += decimalToString(i.getImmediate());
      }
      if(myTable->RSposition(myOpcode) == position)
      {
        ASMString+=i.getRS();
      }
      if((myTable->RTposition(myOpcode)) == position)
      {
        ASMString += (i.getRT());
      }
      if(position < (myTable -> numOperands(myOpcode)-1)) // comma after every register
      {
        ASMString += ", ";
      }

    }  
  }
//FOR JTYPE INSTRUCTIONS 
else
  {

    if(myTable -> isIMMLabel(myOpcode) == true)     //J type instructions have immediate labels 
    {
      ASMString += decimalToHex(i.getImmediate());  //convert the immedaite to its hexadeciaml representation 

    }

  } 
 // cout <<"My decoded instructions are " <<ASMString << endl; 

  return ASMString;
}