Java Setter为类中的每个对象设置值

Java Setter为类中的每个对象设置值,java,setter,Java,Setter,我有一个程序,将学生的姓名和成绩作为用户输入,然后对其执行一些与问题范围无关的操作。代码如下: import java.io.*; import java.util.Arrays; import java.util.Scanner; public class Student { // Four attributes that define Student private String name; private double points; private int startYear; pri

我有一个程序,将学生的姓名和成绩作为用户输入,然后对其执行一些与问题范围无关的操作。代码如下:

import java.io.*;
import java.util.Arrays;
import java.util.Scanner;

public class Student {
// Four attributes that define Student
private String name;
private double points;
private int startYear;
private int[] grades;

public Student(String name, double points, int startYear, int[] grades) {
    this.name = name;
    this.points = points;
    this.startYear = startYear;
    this.grades = grades;
}
//Constructor. Everyone starts with 0 points and this year

public static void main(String[] args) {
    Scanner sc = new Scanner(System.in); //Create scanner
    System.out.println("Please enter the number of students:");
    int count = sc.nextInt(); // Number of students
    System.out.println("Please enter the number of grades:");
    int count1 = sc.nextInt(); // Number of grades
    Student students[] = new Student[count]; // Create array of student objects based on previously entered value
    int[] temp = new int[count1]; // Temporary array for storing grades entered
    for (int i = 1; i < count + 1; i++) {
        System.out.println("Please enter the name of student " + i);
        String name = sc.next();
        students[i - 1] = new Student(name,0.0,2018,temp); // Creating student object
        System.out.println("Please enter grades of  " + name);
        for (int k = 0; k < count1; k++) {
            int personal_grades = sc.nextInt();
            temp[k] = personal_grades; //filling the temporary array
            //System.out.println(grades.length); //for debugging

        }
        students[i - 1].setGrades(temp); //transferring from temporary array to student object array
        students[i-1].printGrades();

    }
    System.out.println((students[0].name));
    System.out.println((students[1].name));
    System.out.println(Arrays.toString(students[0].grades));
    System.out.println(Arrays.toString(students[1].grades));
    for(int i = 0; i < count; i++) {
        System.out.println("Grades of  " + students[i].name + " are:");
        //students[i].printGrades();
    }
    for(int i = 0; i < count; i++) {
        System.out.println("Average of  " + students[i].name + " is:");
       // students[i].average();
    }
    int passed=0;
    for(int i = 0; i < count; i++) {

        if(students[i].average()>5.5)
        {
            passed++;

        }

    }
    System.out.println(passed+" students passed!");


}

public void setGrades(int[] temp) {

        this.grades = temp;


}

public int[] getGrades() {
    return grades;
}

public void printGrades() {


        System.out.println(Arrays.toString(grades));

    }

public float average (){
    int k = 0;
    int sum=0;
    float average=0;
    while (k < this.grades.length) {
        sum=sum+this.grades[k];
       k++;

    }
    average = sum/(float)this.grades.length;
    System.out.println(average);
    return average;
}
}
import java.io.*;
导入java.util.array;
导入java.util.Scanner;
公立班学生{
//定义学生的四个属性
私有字符串名称;
私人双积分;
私人int startYear;
私人机构内部职系;;
公立学生(字符串名称、双倍分数、整数起点、整数[]分数){
this.name=名称;
这个点=点;
this.startYear=startYear;
这个。等级=等级;
}
//构造器。每个人从0分开始,今年
公共静态void main(字符串[]args){
Scanner sc=新扫描仪(System.in);//创建扫描仪
System.out.println(“请输入学生人数:”);
int count=sc.nextInt();//学生人数
System.out.println(“请输入分数:”);
int count1=sc.nextInt();//等级数
Student students[]=new Student[count];//基于先前输入的值创建Student对象数组
int[]temp=new int[count1];//用于存储输入成绩的临时数组
对于(int i=1;i5.5)
{
通过++;
}
}
System.out.println(通过+“学生通过!”);
}
公共空间设置等级(内部[]温度){
这个等级=温度;
}
公共int[]getGrades(){
返回等级;
}
公共服务职系(){
System.out.println(array.toString(grades));
}
公众浮动平均值(){
int k=0;
整数和=0;
浮动平均值=0;
而(k
我在代码中遇到的问题如下:setter方法似乎为曾经创建的所有对象设置值。以此测试运行为例:

您可以看到,每个学生的记录中都会显示上次输入的学生的成绩。我已经调试并发现是
setGrades
方法导致了这种情况。但是,我正在使用
this
关键字-为什么它会设置所有对象的值呢?

将包含分数的数组(
temp
)移动到创建单个学生的循环中

for (int i = 1; i < count + 1; i++) {
    ...
    int[] temp = new int[count1];  //The array holding the grades must be *specific* for each student

    students[i - 1] = new Student(name, 0.0, 2018, temp); // Creating student object
    ...
    students[i - 1].setGrades(temp); //transferring from temporary array to student object array
    students[i - 1].printGrades();

}
for(int i=1;i
在原始代码中,您只使用了一个数组,即
temp
始终指向同一个数组。完成初始化第一个学生后,当循环填充第二个学生的成绩时,您正在变异(或修改)为第一个学生创建的相同成绩数组。

您需要移动

int[] temp = new int[count1]; // Temporary array for storing grades entered

在外部
for
循环中,否则所有创建的
学生将引用相同的成绩数组,并且所有将以最后一个学生的成绩结束。

请注意
学生的构造函数和
学生::setGrades()
如何通过引用获取
成绩

这意味着对于每个
学生
的实例,其
成绩
字段指向初始化期间接收到的参数

但是,您只需初始化一次
temp
,因此所有实例都指向相同的级别数组。更改此数组后,调用
student.printGrades()
将打印共享数组的内容

这可以通过在每次迭代中初始化
temp
,然后创建新的
Student
实例来解决;或者通过在
setGrades()内按值复制数组
方法:

public void setGrades(int[] temp) {
    this.grades.clone(temp);
}

这是因为对每个人的所有等级使用相同的数组

移动的
temp=newint[count1]应该修复它