用代码算水费

故事的开始

不知不觉在合租房中就混成了资历最老的住户,而算水费的工作也很自然的落在了我的头上。因为合租房中人员流动性很强,水费又攒了四个月没交,经过统计2017年12月到2018年3月这段时间共有11人需要交水费。于是算水费成了一件略头疼的事情。

算水费麻烦在于大家的时间都不一样。比如之前主卧到期了,主卧有一段时间空闲,然后住进来三个人中间又走了一个人。这只是主卧的情况,其他房间也都存在这种情况。

思路

这件事情首先需要想清楚思路。计算水费除非给每个人安一个水表是不能达到完全公平的,那么首先假定每人每天(人/天,这个单位很重要)用的水费都是一样的。平均算水费的关键在于这一段时间里一共有多少个人/天,用总钱数除掉所有的人/天,得到的就是每人/天的钱数,然后用每个人的天数乘以每人/天的钱数就是每个人要交的水费啦~

例子:有威尔逊和薇洛两个人合租。威尔逊住了一天,薇洛住了两天。水费一共9块,那么一共有3人/天,每人/天的水费是9/3=3,然后威尔逊的水费是31=3,薇洛的水费是32=6。

感觉完全是小学的数学题啊,其实就是计算略麻烦,用电脑算起来稍微简单点罢了。好了,思路捋清楚了就开始动手写代码了。

代码需要有两个输入,一是总钱数,二是每个人住的时间段。需要有一个输出是每个人要交的水费是多少。

代码

输入

最开始采用了控制台的输入方式。

private void inputFromConsole() {
    Scanner scanner = new Scanner(System.in);
    allMoney = Integer.parseInt(scanner.nextLine());

    String nextLine = scanner.nextLine();
    while(!nextLine.equals("0")) {
        try {
            String name = nextLine.split(" ")[0];
            String time = nextLine.split(" ")[1];
            String from = time.split(":")[0];
            String end = time.split(":")[1];
            int days = Utils.countInterval(from, end) + 1;
            System.out.println("name:" + name + ",days:" +  days);
            waterBillList.add(new WaterBill(name, time, days, null));

            nextLine = scanner.nextLine();
        } catch (Exception e) {
            //加一个容错,如果输入格式不对。可以重新输入。
            nextLine = scanner.nextLine();
        }
    }
}

但是控制台输入方式太费劲,还容易出错。后来就改成了从excel中读取。

private void inputFromExcel(){
    try {
        FileInputStream inputStream = new FileInputStream(new File(excelFileName));
        //读取工作簿
        XSSFWorkbook workBook = new XSSFWorkbook(inputStream);
        //读取工作表
        XSSFSheet sheet = workBook.getSheetAt(0);
        for (int i = 1; i < sheet.getLastRowNum(); i++) {
            XSSFRow row = sheet.getRow(i);
            XSSFCell cellName = row.getCell(0);
            String name = cellName.getStringCellValue();
            XSSFCell cellTime = row.getCell(1);
            String time = cellTime.getStringCellValue();

            String from = time.split(":")[0];
            String end = time.split(":")[1];
            int days = Utils.countInterval(from, end) + 1;
            System.out.println("name:" + name + ",days:" +  days);

            XSSFCell cellDay = row.getCell(2);
            cellDay.setCellValue(days);


            waterBillList.add(new WaterBill(name, time, days, null));
        }

        allMoney = sheet.getRow(sheet.getLastRowNum()).getCell(1).getNumericCellValue();

        workBook.write(new FileOutputStream(new File(excelFileName)));

        inputStream.close();
        workBook.close();//最后记得关闭工作簿
    } catch (Exception e) {
        e.printStackTrace();
    }
}

计算

计算其实很简单,没几行代码。总之就是先算出每人/天的钱数,然后乘以每人的天数。

private void count() {
    int allPersonOfDay = 0;
    for (int i = 0; i < waterBillList.size(); i++) {
        allPersonOfDay += waterBillList.get(i).getDays();
    }
    double averageMoney = allMoney / allPersonOfDay;

    System.out.println("结果:");

    for (int i = 0; i < waterBillList.size(); i++) {
        String name = waterBillList.get(i).getName();
        String bill = String.format("%.2f", averageMoney * waterBillList.get(i).getDays());
        waterBillList.get(i).setBill(bill);

        System.out.println("名字:" + name + ",账单:" + bill);
    }
//        createAndOutPutExcel(waterBillList);
    outPutExcel(waterBillList);
}

输出

最后把结果输出的excel表格里,便于查看。

    private void outPutExcel(List waterBills) {
        try {
            FileInputStream inputStream = new FileInputStream(new File(excelFileName));
            //读取工作簿
            XSSFWorkbook workBook = new XSSFWorkbook(inputStream);
            //读取工作表
            XSSFSheet sheet = workBook.getSheetAt(0);


            for (int i = 0; i < waterBills.size(); i++) {
                XSSFRow row = sheet.getRow(i + 1);
                XSSFCell cellName = row.getCell(3);
                cellName.setCellValue(waterBills.get(i).getBill());
            }

            workBook.write(new FileOutputStream(new File(excelFileName)));

            inputStream.close();
            workBook.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

示例

计算需要按照水费单的两个月为一个周期,下面就只使用12月和1月的水单为示例。

首先整理一个表格把人名和对应的天数放进去。


image

点击运行就出来结果了。


image

最后

排版可以说惨不忍睹了。这件事也算是有点意思吧,解决现实生活中的问题了。

代码可以在这里下载 http://p06iwel4h.bkt.clouddn.com/waterBill.zip

欢迎关注【Funny新青年】微信公众号~

你可能感兴趣的:(用代码算水费)