add fields to a class java(scalability)

Discussion in 'Tech Discussion' started by lichdeath, Nov 9, 2017.

  1. lichdeath

    lichdeath undead meatbun ^^

    Joined:
    Apr 18, 2016
    Messages:
    780
    Likes Received:
    744
    Reading List:
    Link
    so im trying to figure out how to add fields to a class in java?

    e.g
    i have a program, a user and it has this class :

    public class Person {
    String firstName;
    String lastName;

    now my user would like to permanently add the age to the class Person so that it looks like this:

    public class Person {
    String firstName;
    String lastName;
    int age;

    how do i do it?
     
  2. Needhydra

    Needhydra Everything is on Fire

    Joined:
    Jan 19, 2016
    Messages:
    171
    Likes Received:
    81
    Reading List:
    Link
    um do you mean hard code or at run-time dynamically add variables?
     
  3. Needhydra

    Needhydra Everything is on Fire

    Joined:
    Jan 19, 2016
    Messages:
    171
    Likes Received:
    81
    Reading List:
    Link
    well any ways ill assume the latter for now. Use a Map<String, Object>
    the string will be the name and the object is what ever object data you want example would be

    Map<String, Object> map=new HashMap<String, Object> ();
    map.push(Age, new Integer(2))

    Using a flat file database like sqlite to save data as a flat file database would be a great way to save data or idk use a csv.
     
    Last edited: Nov 9, 2017
  4. lichdeath

    lichdeath undead meatbun ^^

    Joined:
    Apr 18, 2016
    Messages:
    780
    Likes Received:
    744
    Reading List:
    Link
    hrm... well i can make it and all but i dont see how it adds the age to the class?
     
  5. Jeebus

    Jeebus Well-Known Member

    Joined:
    Jun 20, 2017
    Messages:
    904
    Likes Received:
    780
    Reading List:
    Link
    @Needhydra's way works if you need to add age on-the-fly. If you know before compiling that age is an optional parameter, you could try overloading your constructor.

    So, in your Person class, you have two constructors and the related variables declared and get and set methods:
    Code:
    public Person (String firstNameIn, String lastNameIn) {
       setFirstName(firstNameIn);
       setLastName(lastNameIn);
    }
    public Person (String firstNameIn, String lastNameIn, int ageIn) {
       setFirstName(firstNameIn);
       setLastName(lastNameIn);
       setAge(ageIn);
    }
    
    Then in your main, you can choose between the two depending on what parameters are required.
    Code:
    Person person1 = new Person("Bob", "Smith", 23);
    Person person2 = new Person("Barbara", "Doe");
    You can also use the setAge method on either.

    Here are two classes that will accomplish this for you:
    Code:
    public class Person {
        private String firstName, lastName;
        private int age;
     
        //Default constructor
        public Person() {
        }
    
        //Constructor without age
        public Person(String firstNameIn, String lastNameIn) {
            setFirstName(firstNameIn);
            setLastName(lastNameIn);
        }
    
        //Overloaded constructor with age
        public Person(String firstNameIn, String lastNameIn, int ageIn) {
            setFirstName(firstNameIn);
            setLastName(lastNameIn);
            setAge(ageIn);
        }
    
        //Get and set methods. If you're going to really use this, add error checking.
        public String getFirstName() {
            return firstName;
        }
    
        public void setFirstName(String firstNameIn) {
            firstName = firstNameIn;
        }
    
        public String getLastName() {
            return lastName;
        }
    
        public void setLastName(String lastNameIn) {
            lastName = lastNameIn;
        }
    
        public int getAge() {
            return age;
        }
    
        public void setAge(int ageIn) {
            age = ageIn;
        }
    }
    
    Code:
    public class Main extends Person{
        public static void main(String[] args) {
            // Use two different overloaded constructors with age as an optional parameter.
            Person person1 = new Person("Bob", "Smith");
            Person person2 = new Person("Barbara", "Doe", 32);
    
            //Add age to person1 even though it wasn't part of the constructor.
            person1.setAge(22);
    
            //Now person1 has an age.
            System.out.printf("%s is %d.", person1.getFirstName(), person1.getAge());
    
        }
    }
    
     
    Last edited: Nov 10, 2017
  6. Needhydra

    Needhydra Everything is on Fire

    Joined:
    Jan 19, 2016
    Messages:
    171
    Likes Received:
    81
    Reading List:
    Link
    you cant add variables after the program is complied so you need a map that can assign a "variable" name and some kind of data to it. you need to write a bunch of cases to deal with all the different data types. you also need to have a file somewhere in order to load from to save the data structure in the map
     
    Last edited: Nov 10, 2017
  7. Needhydra

    Needhydra Everything is on Fire

    Joined:
    Jan 19, 2016
    Messages:
    171
    Likes Received:
    81
    Reading List:
    Link
    a map kinda works like a list
     
  8. Jeebus

    Jeebus Well-Known Member

    Joined:
    Jun 20, 2017
    Messages:
    904
    Likes Received:
    780
    Reading List:
    Link
    To add to @Needhydra, Java is a compiled language. Once you compile your source into binary, what's there is there, and what's not is not. You can't retroactively add a variable to a program without updating your source and recompiling. You can try your luck with lists, linked lists, array lists, and maps, but they're more like duct taped solutions for your usecase.
     
    Last edited: Nov 10, 2017
  9. Truerror

    Truerror Well-Known Member

    Joined:
    Jan 10, 2016
    Messages:
    546
    Likes Received:
    292
    Reading List:
    Link
    Reflection is a thing. Don't specifically know how to do it in Java, but it is possible in C#, so I imagine you could do the same thing in Java too.
     
  10. Jeebus

    Jeebus Well-Known Member

    Joined:
    Jun 20, 2017
    Messages:
    904
    Likes Received:
    780
    Reading List:
    Link
    Reflection can be used, but I'd recommend against it if you only want to permanently add a single class variable. Reflection is more useful for dynamically generating a class at runtime based on the system that's running it or on factors that you can't account for directly in your code. You can also look at using BCEL or Byte Buddy. I'm still of the opinion that if you only want to add a single variable, your best bet is to just update your code and recompile it.
     
    Last edited: Nov 10, 2017
  11. lichdeath

    lichdeath undead meatbun ^^

    Joined:
    Apr 18, 2016
    Messages:
    780
    Likes Received:
    744
    Reading List:
    Link
    k i got it to work which is nice ...
    but i dont think its really efficient if i want to expand my code and do the same with 70 other classes....
     
  12. Jeebus

    Jeebus Well-Known Member

    Joined:
    Jun 20, 2017
    Messages:
    904
    Likes Received:
    780
    Reading List:
    Link
    What's your usecase, and what method did you end up using?
     
  13. Needhydra

    Needhydra Everything is on Fire

    Joined:
    Jan 19, 2016
    Messages:
    171
    Likes Received:
    81
    Reading List:
    Link
    Sounds like you should use a database and gave 1 class that can process the data. Or dev a web app so when ever a user breaks something you can fix it quickly.
     
  14. Truerror

    Truerror Well-Known Member

    Joined:
    Jan 10, 2016
    Messages:
    546
    Likes Received:
    292
    Reading List:
    Link
    True, but I'm not about to make any assumption about his case. I mentioned reflection because it sounds like that's what he wants. As for what he actually needs, that's another matter entirely.

    Besides, I doubt he'd actually use reflection just to add a single variable that he knows beforehand. Nobody does that. :LOL:
     
  15. Jeebus

    Jeebus Well-Known Member

    Joined:
    Jun 20, 2017
    Messages:
    904
    Likes Received:
    780
    Reading List:
    Link
    For reference, if the OP wants to use reflection in Java to execute runtime injection for his stated case, he'd need to create a class that runs premain and creates a sub of whatever class he wants to modify. Then, he'd have to run a proxy in his main that redirects any calls to the super to the sub. Also, he'd have to build the variables and methods for the sub line-by-line with reflection and either bytecode or something like Byte Buddy. It's non-trivial, and in most cases, it adds unneeded complexity to your code. To be sure, there are some great uses, like security checks or loading modules on-demand, but the case described by the OP doesn't fall into the categories that are generally useful with runtime injection.

    A lot of people come at Java like they'd approach JS or Python, where it's basically trivial to manipulate your code at runtime. I'm going to go out on a limb and assume that's what the OP was hoping for here.
     
    Last edited: Nov 11, 2017
  16. Truerror

    Truerror Well-Known Member

    Joined:
    Jan 10, 2016
    Messages:
    546
    Likes Received:
    292
    Reading List:
    Link
    Sounds very complicated. I guess I'm lucky that .NET has reflection built into the framework.
     
  17. Jeebus

    Jeebus Well-Known Member

    Joined:
    Jun 20, 2017
    Messages:
    904
    Likes Received:
    780
    Reading List:
    Link
    Reflection is built into Java, too. It's just not really made for runtime injection. Instead, it's more useful for things like enumerating get and set methods in a binary or Spring serverlets for which there is no available documentation.
     
  18. Truerror

    Truerror Well-Known Member

    Joined:
    Jan 10, 2016
    Messages:
    546
    Likes Received:
    292
    Reading List:
    Link
    Oh. Well, I've to admit that even though System.Reflection can be used to build custom types at runtime, I've never actually used it. Just haven't been in a situation where I have to use it. So I guess it's fine even if Java doesn't have it. I suppose it's just not in their priority list.