1
votes

Évitez la même valeur dans l'argument de paramètre dans l'objet

Supposons que je crée un objet en Java comme celui-ci

Student std1 = new Student("Tom", "male");

Je dois empêcher qu'un autre objet (tel: std2, std3, etc.) ait la même valeur que std1. Comment faire?

[modifier] L'exemple de ce que je veux est:

interdit: Student std2 = new Student ("Tom "," male ");

autorisé: Student std2 = new Student (" Not Tom "," male "); ou Student std2 = new Student ("Tom", "female"); ou Student std2 = new Student ("John", "male"); , etc p>

Merci


4 commentaires

Non, vous n'avez pas besoin de cela / devriez le faire. Ce que vous voudrez peut-être, c'est interdire à une deuxième instance Student avec les mêmes données d'être persistante ou ajoutée à un Course ou autre chose, mais vous devriez pas interdire la création de l’objet lui-même.


nouvel étudiant ("Tom", "femme") ou nouvel étudiant ("pas Tom", "homme") est-il autorisé? Ce que vous entendez par "la même valeur" n'est pas clair ...


Je pense que vous avez besoin d'un identifiant intégré. Si vous essayez de créer un objet avec des valeurs en double, cela ne sera pas autorisé.


Vous pouvez créer un String HashSet statique en y ajoutant un nom concaténé, un sexe. Ainsi, les données de votre HashSet ressembleront à Tom, homme , Tom, femme , John, homme . Et dans le constructeur paramétré de votre classe Student, vous pouvez vérifier le HashSet s'il ne contient pas de nom, de sexe, puis instancier et objet. Quelque chose comme ca!


4 Réponses :


0
votes

Vous pouvez créer une classe qui contrôlera la création de l'objet - utilisez essentiellement un modèle de poids mouche.

Étape 1. Rendez le constructeur du package Student-private

public class StudentPool {
    private List<Student> students = new ArrayList<>();

    public Student getOrCreate(String name, String gender) {
        Student student = new Student(name, gender);
        return students.stream()
                .filter(s -> Objects.equals(s, student))
                .findFirst()
                .orElseGet(() -> {
                    students.add(student);
                    return student;
                });
    }

    public List<Student> get(String name) {
        return students.stream()
                .filter(student -> Objects.equals(student.getName(), name))
                .collect(Collectors.toList());
    }
}

Étape 2. Implémentation de la méthode equals dans Student

   public boolean equals (Object other) {
       if (!(other instanceof Student)) return false;
       Student otherStudent = (Student) other;
       return Objects.equals(otherStudent.getName(), this.getName()) && Objects.equals(otherStudent.getGender(), this.getGender());
   }

Étape 3. Implémentation d'un pool d'objets Student dans le même package

public class Student {
    Student(String name, String gender) {
    ...


1 commentaires

Étant donné que l'OP veut que la combinaison nom + sexe soit unique (pas seulement le nom), vous devez créer une clé combinant ces deux valeurs plutôt que d'utiliser le nom comme clé



0
votes

En supposant que par "valeur" vous faites référence au nom des élèves, je vous suggère d'écrire une petite fonction qui retournera vrai si le nom est déjà pris. Pour ce faire, vous pouvez stocker tous vos "étudiants" dans une ArrayList:

if (!nameIsAlreadyTaken(students, newName)){
students.add(new Student(newName, newGender));
} else{
    //something you want to to if the name is already taken
}

Vous pouvez maintenant ajouter des étudiants à cette ArrayList comme suit:

private boolean nameIsAlreadyTaken(ArrayList<Student> students, String newName){
    for (int i = 0; i < student.size(); i++){
        if(students.get(i).getName().equals(newName)){
            return true;
        }
    }
    return false;
}


0 commentaires

0
votes

Vous pouvez créer un String HashSet statique en y ajoutant un nom concaténé, un sexe.

if(!YourClass.studentExists(name, gender)) {
    Student student = new Student(name, gender);
}

Ainsi, les données de votre HashSet ressembleront à Tom, homme, Tom, femme, John, homme.

class Student {
...

public Student(String name, String gender) {
    this.name = name;
    this.gender = gender;
    YourClass.addStudent(name, gender);
  }
}

Et pendant la création une instance de Student, vous pouvez vérifier le HashSet si celui-ci ne contient pas de nom, de sexe, puis d'instancier et d'objet.

class YourClass {
   public static Set<String> studentSet = new HashSet<>();

   public static void addStudent(String name, String gender) {
     YourClass.studentSet.add(name + "," + gender);
   }

   public static Boolean studentExists(String name, String gender) {
     return YourClass.studentSet.constains(name + "," + gender);
}

J'espère que cela résout votre problème


0 commentaires

0
votes

Je dirais que vous devez remplacer les méthodes equals et hashCode de Student , puis vérifier dans le constructeur si un tel étudiant existe . Bonne réponse sur ce point: lien .

class Student {
    private static final Set<Student> REGISTERED_STUDENTS = new ConcurrentSkipListSet<>(Comparator.comparing(Student::getName).thenComparing(Student::getGender));

    private String name;
    private String gender;

    public static Set<Student> getRegisteredStudents() {
        return Collections.unmodifiableSet(REGISTERED_STUDENTS);
    }

    public static void addStudent(final String name, final String gender) {
        Student probablyExists = new Student(name, gender);
        REGISTERED_STUDENTS.add(probablyExists);
    }

    private Student(final String name, final String gender) {
        this.name = name;
        this.gender = gender;
    }

    public String getName() {
        return name;
    }

    public String getGender() {
        return gender;
    }

    @Override
    public int hashCode() {
        return Objects.hash(name, gender);
    }

    @Override
    public boolean equals(final Object o) {
        if (this == o) return true;
        if (!(o instanceof Student)) return false;
        final Student student = (Student) o;
        return Objects.equals(name, student.name) && Objects.equals(gender, student.gender);
    }
}

Veuillez noter que cet exemple est n'est pas thread-safe et utilise une solution discutable consistant à lancer une exception directement dans le constructeur. Vous voudrez probablement une méthode d'usine et ConcurrentSkipListSet ou une autre collection thread-safe, comme ceci:

import java.util.*;

public class Student {
    private static final Set<Student> REGISTERED_STUDENTS = new HashSet<>();

    private String name;
    private String gender;

    public static Collection<Student> getRegisteredStudents() {
        return Collections.unmodifiableCollection(REGISTERED_STUDENTS);
    }

    public Student(final String name, final String gender) {
        this.name = name;
        this.gender = gender;

        if (REGISTERED_STUDENTS.contains(this))
            throw DuplicateStudentException();

        REGISTERED_STUDENTS.add(this);
    }

    @Override
    public int hashCode() {
        return Objects.hash(name, gender);
    }

    @Override
    public boolean equals(final Object o) {
        if (this == o) return true;
        if (!(o instanceof Student)) return false;
        final Student student = (Student) o;
        return Objects.equals(name, student.name) && Objects.equals(gender, student.gender);
    }
}


0 commentaires