MySQL按時間統計報表,時間連續沒有數據就補0

祝大家1024節日快樂!

趁着公司斷網這點時間,寫了一篇博客和大家分享一下。。。。。

最近遇到一個問題就是做了一個報表的統計,下面拆分一下需求,簡單的來說一說,就是統計一段時間內的數據量,可以當成是統計10月份每一天的訪問量,要求如果當天的訪問量是0的話,也要統計出來,不能跳過去。時間是連續的。

其實統計這個好做,就是group by +count就可以了,重要的是在當天的數據沒有的話,分組裏面就沒有,然後0當然也出不來。所以就去網上搜了一些資料,這裏總結一下前輩們的思路,詳細的解釋可以戳下面的連接,我就不在多囉嗦一遍了。

  1. 有一個單獨的表存日曆,到時候我們按照時間區間去連接這個表,因爲日曆表裏面的時間是連續的。得到結果也就自然連續了。(從數據庫角度出發,需要單獨去維護一個數據表)
  2. 去連接一個足夠大的帶有日期的數據表,其實這就是相當於把這個表當成了一個日曆表,但是這個表也有可能在某一天沒有數據,那這樣日期也就不連續了
  3. 從程序的角度出發,用代碼去吧0補上,挨個檢查有沒有這天的數量,沒有的話就填個0。需要寫個循環。

https://blog.csdn.net/ajian759447583/article/details/61421399

https://blog.csdn.net/jie11447416/article/details/50887888

我的解決思路呢是受到第一篇大佬博客末尾的啓發,用的union all ,用Java生成的時間片段。

在這裏插入圖片描述

就是這個方法,中間的時間片段我用java生成,給mybatis傳一個list,然後foreach循環生成union。

java時間分片的方法

/**
     * 日期範圍 - 切片
     *  
     *
     * @param startDate 起始日期
     * @param endDate   結束日期
     * @param type 切片類型 1年  2月  3日  4小時
     * @return          切片日期
     */
	public static List<String> sliceUpDateRange(String startDate, String endDate ,int type ) {
		List<String> rs = new ArrayList<>();

		try {
			int dt = Calendar.DATE;
			String pattern = "yyyy-MM-dd";
			if (type==1) {
				pattern = "yyyy";
				dt = Calendar.YEAR;
			} else if (type==2) {
				pattern = "yyyy-MM";
				dt = Calendar.MONTH;
			} else if (type==3) {
				pattern = "yyyy-MM-dd";
				dt = Calendar.DATE;
			}else if (type==4) {
				pattern = "yyyy-MM-dd HH";
				dt = Calendar.HOUR_OF_DAY;
			}
			SimpleDateFormat sd = new SimpleDateFormat(pattern);
			Calendar sc = Calendar.getInstance();
			Calendar ec = Calendar.getInstance();
			sc.setTime(sd.parse(startDate));
			ec.setTime(sd.parse(endDate));
			while (sc.compareTo(ec) < 1) {
				rs.add(sd.format(sc.getTime()));
				sc.add(dt, 1);
			}
		} catch (ParseException e) {
			e.printStackTrace();
		}
		return rs;
	}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章