日曆(設計構造器與預設構造器)
日曆(預設構造器)
要求:
做一個日曆,功能和電腦、手機上的日曆一樣,能顯示每個月的天數,1至12月每個月的天數都能正確顯示(包括閏年2月29天,平年2月28天)。然後每個月的每一號顯示該天對應的星期數。
程式碼:
package com.softeem.lesson06.oop;
/**
* 建立一個方法,獲取一個指定年份,月份當月的總天數
* @author admini
*
*/
public class MyCalendar {
//判斷是否是閏年
public boolean isLeapYear(int year){
return (year % 4 == 0 && year % 100 != 0)|year % 400 == 0;
}
//判斷每個月的天數
public int getDaysOfMonth(int y,int m) {
switch(m) {
case 4:
case 6:
case 9:
case 11:
return 30;
case 2:
//是閏年返回29,不是則返回28
return isLeapYear(y)?29:28;
default:
return 31;
}
}
/**
* 計算從1900年1月份到引數的年份月份上一個月的總天數
* @param y
* @param m
* @return
*/
public int getTotalDaysFrom1900(int y,int m) {
//區域性變數使用前必須先初始化
int days = 0;;
//計算整年的總天數1900~(y-1)
for(int i = 1900;i < y;i++) {
//是閏年加366,否則加365
days += isLeapYear(i)?366:365;//days = days + 366/365
}
//計算從1-(m-1)月的總天數
for(int i = 1;i < m;i++) {
days += getDaysOfMonth(y, i);//days = days + 28/29/30/31
}
return days;
}
/**
* 列印日曆
* @param args
*/
public void printCalendar(int y,int m) {
//獲取列印日曆之前需要預留的空格數
//通過1900年到(y-1)年的總天數除以7來判斷預留數(1900年1月1日正好對應星期一)
int space = getTotalDaysFrom1900(y,m) % 7;
//獲取目標月份的總天數
int days = getDaysOfMonth(y,m);
//用表格的方式呈現日曆,更符合實際,也更美觀
System.out.println("===========SOFTEEM【"+y+"]年【"+m+"】月================");
//天數的最上一排顯示星期數
System.out.println("一\t二\t三\t四\t五\t六\t日");
System.out.println("===================================================");
int count = 0;
//列印日期,用“\t"留出該月份需要預留的空格數
for(int i = 0;i < space;i++) {
System.out.print("\t");
count++;
}
//列印日期
for(int i = 1;i <=days; i++) {
count++;
System.out.print(i +"\t");
//是否達到周天,達到周天則換一行
if(count == 7){
System.out.println();
//計數器歸零,再在下一輪重新判斷是否達到周天
count = 0;
}
}
}
public static void main(String[] args) {
// TODO Auto-generated method stub
//定義新物件
MyCalendar mc = new MyCalendar();
//判斷2019是否是閏年
boolean b = mc.isLeapYear(2019);
//是閏年列印“是”,否則列印“不是"
System.out.println(b?"shi":"bushi");
//定義2020年2月的天數
int days = mc.getDaysOfMonth(2020, 2);
//列印得到的結果
System.out.println(days);
//從1900年1月1日到2020年11月前的總天數
days = mc.getTotalDaysFrom1900(2020,11);
System.out.println(days);
//列印2020年11月的日曆,是日曆編寫的總程式,可以通過設定引數得到我們想要月份的日曆
mc.printCalendar(2020,11);
}
}
執行結果:
日曆(設計構造器)
與預設的日曆的程式基本設計一致,只是這裡通過自己設計構造器的引數來達到降低編碼的複雜度的目的。通過構造器賦值給全域性變數不用再設定多個引數和區域性變數。
程式碼:
package com.softeem.lesson07.example;
public class MyCalendar {
int year;
int month;
//定義構造器的引數,通過構造器直接將引數的數值直接賦值給全域性變數
public MyCalendar(int _year,int _month) {
year = _year;
month = _month;
}
/**
* 判斷指定的年份是否是閏年
*
* @param year
* @return
*/
public boolean isLeapYear(int year) {
return year % 4 == 0 && year % 100 != 0 || year % 400 == 0;
}
/**
* 根據提供的年份月份,返回當前月的總天數
*
* @param y
* @param m
* @return
*/
public int getDaysOfMonth(int y, int m) {
switch (m) {
case 4:
case 6:
case 9:
case 11:
return 30;
case 2:
return isLeapYear(y) ? 29 : 28;
default:
return 31;
}
}
/**
* 計算從1900年1月份到目標的年份月份上一個月的總天
*
* @param y
* @param m
* @return
*/
//不用定義該方法內的引數,方法內直接引入全域性變數”month”和“year”
public int getTotalDaysFrom1900() {
// 區域性變數使用前必須先初始化
int days = 0;
// 計算整年的總天數1900~(y-1)
for (int i = 1900; i < year; i++) {
days += isLeapYear(i) ? 366 : 365; // days = days + 366/365
}
// 計算從1-(m-1)月的總天數 1 2 3 4 5 .. 10
for (int i = 1; i < month; i++) {
days += getDaysOfMonth(year, i); // days = days + 28/29/30/31
}
return days;
}
/**
* 列印日曆
*
* @param y
* @param m
*/
public void printCalendar() {
// 獲取列印日曆之前需要預留的空格數
int space = getTotalDaysFrom1900() % 7;
// 獲取目標年份月份的總天數
int days = getDaysOfMonth(year, month);
System.out.println("============SOFTEEM萬年曆 【" + year + "】年【" + month + "】月=============");
System.out.println("一\t二\t三\t四\t五\t六\t日");
System.out.println("====================================================");
int count = 0;
//列印空格
for (int i = 0; i < space; i++) {
System.out.print("\t");
count++;
}
//列印日期
for (int i = 1; i <= days; i++) {
count++;
System.out.print(i + "\t");
//是否達到周天
if(count == 7) {
System.out.println();
//計數器歸零
count = 0;
}
}
}
public static void main(String[] args) {
//只通過定義構造器的引數來實現功能,幾乎不需要定義其他引數
MyCalendar mc = new MyCalendar(2019,11);
mc.printCalendar();
}
}
執行結果:
總結
設計構造器的日曆和預設構造器的日曆實現功能一樣,程式碼長度相近,從日曆這個例子看不出兩種方法的優劣之分。每種方法都有自己獨特的應用,我們能做的不是區分方法的好壞,從而一味推崇一種或者一類方法。而是面對不同的情況,不同的要求,用更方便的方法來實現要求的功能。沒有強調好壞,只是我們通過該方法實現的功能bug更少,更清楚理解整體結構。
我目前能力有限,對該方面的認識可能比價淺顯,只有不斷的學習,才能掌握理解更多的方法,理解透徹後才能更加靈活的運用在實踐中。
相關文章
- C++ 建構函式實戰指南:預設構造、帶引數構造、複製構造與移動構造C++函式
- 構造器
- Java--構造器和構造方法Java構造方法
- java構造器Java
- 14.構造器
- 【lombok】@NoArgsConstructor/@RequirArgsConstructor/@AllArgsConstructor - 生成無參構造器,指定引數構造器或包含所有引數的構造器LombokStructUI
- 03_方法引用與構造器引用
- Effective Java - 靜態方法與構造器Java
- Java構造器 小白版Java
- iOS提供指定構造器iOS
- 設計模式03----構造者模式設計模式
- 3.Contructor(構造器)模式—精讀《JavaScript 設計模式》Addy Osmani著JavaScript設計模式
- 什麼是 Java 構造器?Java
- 物件導向和構造器物件
- Java基礎03 構造器與方法過載Java
- Day31--構造器詳解
- this,構造器,static,final,單例模式單例模式
- 理解 sole() 查詢構造器方法
- java學習之深入構造器Java
- 模型驅動設計的構造塊(上)——DDD模型
- 訪問器於構造器的高階使用
- 物件導向程式設計(C++篇2)——構造物件程式設計C++
- 621. 任務排程器 (構造)
- 小解惑:查詢構造器與集合中的 get 方法
- UG鈑金設計與製造
- 一文了解 Java 中的構造器Java
- 從零構造一臺計算機——硬體模擬器計算機
- 【智慧製造】機器人與智慧製造機器人
- 構造方法構造方法
- 使用 Laravel Eloquent 構造器讓模型更簡潔Laravel模型
- Effective Java - 構造器私有、列舉和單例Java單例
- Mybatis-Plus - 條件構造器 QueryWrapper 的使用MyBatisAPP
- 構造器中呼叫動態繫結的方法
- 原生JavaScript實現造日曆輪子JavaScript
- Spring注入:配置注入(set注入和構造器注入)與註解注入Spring
- 構造點,線結構
- 分散式發號器架構設計分散式架構
- 移動端日曆元件設計與實現元件