C++類和對象下——實現日期類

?前言

????????在學習了類和對象的六大成員函數后,為了鞏固我們學習的知識可以手寫一個日期類來幫助我們理解類和對象,加深對于其的了解。

默認函數

? ? 構造函數

? ? ? ? 既然是寫類和對象,我們首先就要定義一個類,然后根據實際需要來加入類的數據與函數。作為一個日期類,肯定要有時間了,我們采用公元紀年法,存儲三個變量,年 月 日,如下。

class Date
{private:int _year;int _month;int _day;
};

? ? ? ? 注意這里將三個成員變量定義為private:,是為了防止用戶在外面修改,提高安全性。其次這里在每個成員變量前面加了個下劃線。?_year,這里是為了防止后面與函數的參數重名。當然重名也有其他解決方法例如用this.year,也可以。具體選那種看讀者更適合那種編碼風格。

? ? ? ? 寫完上面的變量后,我們第一個想到要寫的函數必定是構造函數了。如下函數

Date(int year=1900, int month=1, int day=1)
{_year = year;_month = month;_day = day;
}

? ? ? ? 注意我們這里寫成了全缺省,這樣做的好處是不用寫無參的構造函數,給每個日期對象都有默認值。

拷貝構造函數

? ? ? ? 其次我們要寫的就是拷貝構造函數。注意這里的形參加了個const,這里加了const一是為了方防止修改形參d,二是為了通用性。如下例子

	Date(const Date& d){_year = d._year;_month = d._month;_day = d._day;}

? ? ? ? 假如我們沒有加const,有下述程序。這段代碼會報錯!為什么呢?d1的類型為const Date,而拷貝構造函數參數類型為Date& d,如果傳參成功,是不是就可以在構造函數的內部修改原本為const類型的變量,違背了基本的定義語法。但用一個const Date類型拷貝初始化是我們需要的場景,為了讓其正常運行,就需要在拷貝構造函數加const。

int main()
{const Date d1(2024, 4, 16);Date d2(d1);return 0;
}

? ? ? ? 有const變量自然也有普通的變量了。我們就可以寫個普通變量的拷貝構造函數。

Date(Date& d)
{_year = d._year;_month = d._month;_day = d._day;
}

? ? ? ? 其實在很多地方會將上面兩個構造函數簡化為一個,即保留含const的

Date(const Date& d)
{_year = d._year;_month = d._month;_day = d._day;
}

? ? ? ? 那自然有人問?普通變量的拷貝怎么辦呢?在這里就不得不提C++對于變量類型的處理了。我們首先看段熟悉的代碼。

int a=0;a=1.12;

? ? ? ? 這段代碼會報錯么?為什么?大家可以在程序中運行下,結果是不會報錯的,有的編譯器可能會有警告。大家知道整型與浮點型在內存中的存儲方式是不一樣的,即使是對浮點型內存的截斷讀取a也不可能為1.

? ? ? ? 但a的結果卻是一,這是因為編譯器幫我們做了類型轉化,稱之為隱式轉換。如下圖。

? ? ? ? 同理當我們將Date變量賦給const Date& d,編譯器也會額外開辟空間付給形參d。

? ? ? ? 或許有讀者又有疑問?Date變量賦給const Date& d可以,為什么const Date變量賦給Date& d不可以,因為前者是將內存的權限放小,而后者是將對內存的權限放大。在C++中將權限放小可以,但把權限放大就有可能產生難以預料的后果。

? ? ? ? 接下來我們來實現與拷貝構造函數功能十分像的賦值重載函數。

賦值重載函數

? ? ? ? 代碼如下

	Date& operator=(const Date& d){if (&d != this){_year = d._year;_month = d._month;_day = d._day;}return *this;}

? ? ? ? 這里我們任然將參數的類型加上const省去對于普通變量與const變量的分類了,當然對于普通變量會隱式轉換,會減少些效率。

? ? ? ? 注意這里將d的地址與this比較,這是為了防止自己和自己賦值的情況如 a=a,這樣沒有任何的意義。

析構函數

? ? ? ? 在這個對象中我們沒有開辟內存,沒有在堆區申請空間,寫不寫析構函數都可以。

~Date()
{}

成員函數

<<重載

? ? ? ? 我們為了后續的方便,首先要實現的便是cout輸出Date類型,對于內置類型cout可以直接的輸出,但是對于自定義類型要我們使用操作符重載.

? ? ? ? 按照習慣我們極大概率會將<<寫在類里面。寫出如下的代碼

ostream& operator<<(ostream& out)
{out << _year << "-" << _month << "-" << _day << endl;return out;
}

? ? ? ? 其中的ostream參數是輸出時要用到的一種類型,返回值為ostream是為了連續輸出的原因。這個看起來沒有什么錯誤,但運行的時候就會報錯!

? ? ? ? 我們明明重載了<<操作符,為什么卻提示我們沒有匹配類型呢?這就不得不提到this了,在使用cout << d1操作符重載的時候,我們從左向右顯然要傳遞兩個參數ostream和Date,在類中的成員函數默認第一個參數傳遞Date,即形參this指針,第二個實參初始化函數的形參。

? ? ? ? 關于this指針詳情可以看【C++ 類和對象 上 - CSDN App】http://t.csdnimg.cn/Wx5iO。在這里就不敘述了。

? ? ? ? 于是上面的代碼也不是不可以用,可以采用如下的方法使用

? ? ? ? 但這種方法顯然是不符合我們日常認知的。

? ? ? ? 為了解決這種問題,我們把<<操作符改為全局函數。就可以解決順序的問題了。如下代碼

ostream& operator<<(ostream& out, const Date& d)
{out << d._year << "年" << d._month << "月" << d._day << "日" << endl;return out;
}

? ? ? ? 但此時又有一個新的問題,這個重載函數不可以訪問Date對象中私有的成員變量,這就體現了我們類的安全性高,為了解決我們需要把這個操作符重載函數聲明為友元函數就可以了。

class Date
{
public:Date(int year=1900, int month=1, int day=1){_year = year;_month = month;_day = day;}Date(const Date& d){_year = d._year;_month = d._month;_day = d._day;}Date& operator=(const Date& d){if (&d != this){_year = d._year;_month = d._month;_day = d._day;}return *this;}friend ostream& operator<<(ostream& out, const Date& d);private:int _year;int _month;int _day;
};

? ? ? ? 這樣我們就可以正常輸出了。

>>重載

? ? ? ? 有了輸出,當然要有其對應的輸入最好。和輸出重載一樣,將>>操作符重載為全局函數,并且在類中聲明為友元函數。

istream& operator>>(istream& in,  Date& d)
{in >> d._year >> d._month >> d._day;return in;
}

? ? ? ? 如下圖,剛開始輸出1900時我們寫的全缺省參數的作用,而后輸出的就是我們輸入的2024 5 13.

? ? ? ? 光有輸入輸出函數顯然是不可以的,我們也要有對應的函數。

大小比較

? ? ? ? 對于一個日期比較大小是符合實際需求的,我們可以寫個cmp成員,但更好的使用操作符重載,< >,這個我們最熟悉又可以減小記憶的負擔。

>比較

? ? ? ? 我們有兩種方法比較兩個日期的大小。

方法一

? ? ? ? 不斷地尋找true條件,最后剩下的就是false。注意年數相等的時候要判斷月份

bool Date::operator>(Date& d)
{if (_year > d._year){return true;}else if (_year == d._year){if (_month > d._month){return true;}else if (_month == d._month){if (_day > d._day){return true;}}}return false;
}
方法二

? ? ? ? 將日期的比較轉換為數的比較。月份最多有12月,天最多有31天,我們就可以將年擴大10000倍,月擴大100倍,將2024年5月13日與2023年4月20日比較轉換為2024513與2023420比較。我們知道數的比較大小是從高位往下開始比較的。這與我們比較日期的順序不謀而合,就可以如下的簡化代碼。

bool Date::operator>(Date& d)
{return _day + _month * 100 + _year * 10000 > d._day + d._month * 100 + d._year * 10000;
}

同理小于等于。大于等于,小于都可以如上比較。

bool Date::operator<(Date& d)
{return _day + _month * 100 + _year * 10000 <d._day + d._month * 100 + d._year * 10000;
}
bool Date::operator<=(Date& d)
{return _day + _month * 100 + _year * 10000 <=d._day + d._month * 100 + d._year * 10000;
}
bool Date::operator>=(Date& d)
{return _day + _month * 100 + _year * 10000 >=d._day + d._month * 100 + d._year * 10000;
}
bool Date::operator!=(Date& d)
{return _day + _month * 100 + _year * 10000 !=d._day + d._month * 100 + d._year * 10000;
}

????????判斷兩個日期是否相等的代碼也十分簡單,如下。

相等判斷

bool Date::operator==(Date& d)
{return _year == d._year&& _month == d._month&& _day == d._day;
}

????????到此我們的比較函數就寫完了。但光有比較還不可以,我們可能想要知道50天后是哪一天,50天前是那一天,兩個日期相差多少天。

加減操作

? ? ? ? 在后續的操作中我們不可避免的要訪問某年某月有多少天,我們便可以將他封裝為成員函數,便于我們查找天數。

獲取天數

? ? ? ? 我們可以將每個月的天數寫在一個數組中,然后哪一個月就讀取哪一個數字,但其中2月十分特殊要分為潤年的問題要單獨判斷下。

int Date::GetMonthDay(Date& d)
{static int arr[13] = { 0,31,28,31,30,31,30,31,31,30,31,30,31 };if (d._month == 2 && ((d._year % 400 == 0) || (d._year % 4 == 0 && d._year % 100 != 0))){return 29;}return arr[d._month];
}

? ? ? ? 這里將數組加上static 是為了避免重復創建,提高效率。然后就是判斷是不是閏年的二月。

+=重載

? ? ? ? 我們可以將一個日期類加上n天返回加n天后的日期。

Date& Date::operator+=(int t)
{_day += t;while (_day > GetMonthDay(*this)){_day -= GetMonthDay(*this);_month++;if (_month == 13){_month = 1;_year++;}}return *this;
}

? ? ? ? 我們整體的循環是在找當前月合理的天數,如果不合理就月份加一,天數減去當前月,繼續判斷直到結束。

? ? ? ? 測試結果正確。

? ? ? ? 大家寫的時候可以用日期計算器 - 天數計算器 | 在線日期計算工具 (sojson.com)這個網站檢測。

+重載

? ? ? ? 我們之前已經寫完+=了,先在寫+的思路是不是與+=類似,我們可以仿照+=寫出+重載,但是我們還有更加簡單的方法,復用+=!!

Date Date::operator+(int t)
{Date t1 = *this;t1 += t;return t1;
}

? ? ? ? 這樣復用代碼就大大簡化了我們寫代碼的復雜度。其實上面的判斷也可以復用代碼,讀者可以自行嘗試。

-=重載

? ? ? ? 一個日期減去一個天數,與一個日前加上一個天數十分像。天數小于肯定是不合理的日期就加上當前月數。不斷的循環判斷直到合理數據。

Date& Date::operator-=(int t)
{_day -= t;while ( _day<1 ){_month--;if (_month == 0){_month = 12;_year--;}_day += GetMonthDay(*this);}return *this;
}

-重載

? ? ? ? 與之前一樣,我們復用-=的函數。

Date Date::operator-(int t)
{Date tmp = *this;tmp -= t;return tmp;
}

? ? ? ? 我們如果對+負數,-負數會怎么樣?顯然程序會崩潰但這又可能是我們使用者的操作,于是便可以在不同的重載函數互相調用。

? ? ? ? 如下代碼

Date Date::operator-(int t)
{if (t < 0)return *this + (-t);Date tmp = *this;tmp -= t;return tmp;
}

? ??日期相減

方法一

? ? ? ? 我們當然會求兩個日期之間的差數。便可以重載-。我們可以對小的天數一直加一直到二者相等。如下

int Date::operator-(Date& d)
{assert(*this >= d);Date t1 = *this;Date t2 = d;int t = 0;//一直加while (t1 != t2){t2 += 1;t++;}return t;
}

? ? ? ? 我們有時也會寫的前一個日期小,導致相差負數,為了達到這種效果也可以對上述代碼稍加修改。

int Date::operator-(Date& d)
{if (*this < d)return d - *this;Date t1 = *this;Date t2 = d;int t = 0;//一直加while (t1 != t2){t2 += 1;t++;}return t;
}
方法二

? ? ? ? 上述的代碼十分簡單,效率有些不理想,我們可以換種方法。

????????首先我們先判斷二者是否相同,不相同在判斷t2的天數是否小于t1,小于說明可能只是天數不同,將天數加到t1的天數,然后判斷是否相等。如果t1的天數等于t2的天數,說明月份不同,將t2的月份一次往上加一判斷二者是否相等。

int Date::operator-(Date& d)
{if (*this < d)return d - *this;Date t1 = *this;Date t2 = d;int t = 0;//一直加while (t1 != t2){int c = GetMonthDay(t2);if (t2._day < t1._day && t1._day <= c){t += t1._day - t2._day;t2._day = t1._day;}else {t2._month++;if (t2._month == 13){t2._year++;t2._month = 1;}t += c - t2._day + 1;t2._day = 1;}}return t;
}

? ? ? ? 這種方法的效率比第一種高了許多。

結語

? ? ? ? 到這里本篇文章就結束了。喜歡的點點關注!

全部代碼如下。

#include<iostream>
#include<assert.h>
using namespace std;class Date
{
public:Date(int year=1900, int month=1, int day=1){_year = year;_month = month;_day = day;}Date(const Date& d){_year = d._year;_month = d._month;_day = d._day;}Date& operator=(const Date& d){if (&d != this){_year = d._year;_month = d._month;_day = d._day;}return *this;}//友元函數聲明friend ostream& operator<<(ostream& out, const Date& d);friend istream& operator>>(istream& in, Date& d);//比較函數bool operator==(Date& d);bool operator>(Date& d);bool operator<(Date& d);bool operator<=(Date& d);bool operator>=(Date& d);bool operator!=(Date& d);//加減操作函數Date& operator+=(int t);Date operator+(int t);Date& operator-=(int t);Date operator-(int t);int operator-(Date& d);int GetMonthDay(Date& d);private:int _year;int _month;int _day;
};//bool Date::operator>(Date& d)
//{
//	if (_year > d._year)
//	{
//		return true;
//	}
//	else if (_year == d._year)
//	{
//		if (_month > d._month)
//		{
//			return true;
//		}
//		else if (_month == d._month)
//		{
//			if (_day > d._day)
//			{
//				return true;
//			}
//		}
//	}
//	return false;
//}
//bool Date::operator<(Date& d)
//{
//	return !(*this >= d);
//}
//bool Date::operator<=(Date& d)
//{
//	return *this < d || d == *this;
//}
//bool Date::operator>=(Date& d)
//{
//	return *this > d || d == *this;
//}
//bool Date::operator!=(Date & d)
//{
//	return !(d == *this);
//}bool Date::operator>(Date& d)
{return _day + _month * 100 + _year * 10000 > d._day + d._month * 100 + d._year * 10000;
}bool Date::operator<(Date& d)
{return _day + _month * 100 + _year * 10000 <d._day + d._month * 100 + d._year * 10000;
}
bool Date::operator<=(Date& d)
{return _day + _month * 100 + _year * 10000 <=d._day + d._month * 100 + d._year * 10000;
}
bool Date::operator>=(Date& d)
{return _day + _month * 100 + _year * 10000 >=d._day + d._month * 100 + d._year * 10000;
}
bool Date::operator!=(Date& d)
{return _day + _month * 100 + _year * 10000 !=d._day + d._month * 100 + d._year * 10000;
}
bool Date::operator==(Date& d)
{return _year == d._year&& _month == d._month&& _day == d._day;
}int Date::GetMonthDay(Date& d)
{static int arr[13] = { 0,31,28,31,30,31,30,31,31,30,31,30,31 };if (d._month == 2 && ((d._year % 400 == 0) || (d._year % 4 == 0 && d._year % 100 != 0))){return 29;}return arr[d._month];
}Date& Date::operator+=(int t)
{if (t < 0)return *this -= (-t);_day += t;while (_day > GetMonthDay(*this)){_day -= GetMonthDay(*this);_month++;if (_month == 13){_month = 1;_year++;}}return *this;
}Date Date::operator+(int t)
{Date t1 = *this;t1 += t;return t1;
}Date& Date::operator-=(int t)
{if (t < 0)return *this += (-t);_day -= t;while ( _day<1 ){_month--;if (_month == 0){_month = 12;_year--;}_day += GetMonthDay(*this);}return *this;
}Date Date::operator-(int t)
{if (t < 0)return *this + (-t);Date tmp = *this;tmp -= t;return tmp;
}int Date::operator-(Date& d)
{if (*this < d)return d - *this;Date t1 = *this;Date t2 = d;int t = 0;//一直加while (t1 != t2){int c = GetMonthDay(t2);if (t2._day < t1._day && t1._day <= c){t += t1._day - t2._day;t2._day = t1._day;}else {t2._month++;if (t2._month == 13){t2._year++;t2._month = 1;}t += c - t2._day + 1;t2._day = 1;}}return t;
}ostream& operator<<(ostream& out, const Date& d)
{out << d._year << "年" << d._month << "月" << d._day << "日" << endl;return out;
}istream& operator>>(istream& in,  Date& d)
{in >> d._year >> d._month >> d._day;return in;
}

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/web/11494.shtml
繁體地址,請注明出處:http://hk.pswp.cn/web/11494.shtml
英文地址,請注明出處:http://en.pswp.cn/web/11494.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

AI編程工具為什么選github copilot?

Github Copilot 是一個奇跡 它的競爭對手&#xff08;Amazon, Google, Meta, 騰訊&#xff09;都是免費的&#xff0c;但每月10-20美元的Github Copilot市場占有率最高。 1、2021年6月上線&#xff0c;比ChatGPT早近一年半 2、GitHub統計&#xff1a; 88%的用戶獲得效率提升平…

element ui的確認提示框文字樣式修改

修改確認提示框文字樣式修改&#xff0c;使用message屬性修改&#xff1a; 例&#xff1a; js代碼&#xff1a; this.$msgbox({title: 確定要刪除嗎?,message: this.$createElement(p, null, [this.$createElement(span, { style: color: red }, 該素材一旦刪除&#xff0c;…

Spring Boot日志

目錄 一、日志概述 1、為什么要學習日志&#xff1f; 2、日志的用途 &#xff08;1&#xff09;系統監控 &#xff08;2&#xff09;數據采集 &#xff08;3&#xff09;日志審計 二、日志使用 1、打印日志 &#xff08;1&#xff09;在程序中得到日志對象 &#xf…

QNX SLM介紹

QNX SLM SLM是Qnx中用來加載Application的組件&#xff0c;它可以監控Application行為&#xff08;比如異常退出時重新Application拉起&#xff09;、控制Application間的啟動時序。 QNX的SLM與Android RC文件類似。 下面摘自QNX官網介紹 System launch and monitor: launch c…

Redis日常維護流程及技巧:確保穩定性與性能

目錄 一、監控和報警設置 1.實時監控&#xff1a;洞察Redis的脈搏 &#xff08;1&#xff09;. 資源使用監控 &#xff08;2&#xff09;. 數據訪問模式監控 &#xff08;3&#xff09;. 持久化監控 &#xff08;4&#xff09;. 客戶端連接 2.報警機制&#xff1a;快速響…

標準Modbus TCP雙網口開關量模塊

M140E以太網遠程I/O無線數據采集模塊是一款工業級、隔離設計、高可靠性、高穩定性和高精度數據采集模塊&#xff0c;嵌入式32位高性能微處理器MCU&#xff0c;集成2路工業10/100M自適應以太網模塊里面。提供多種I/O&#xff0c;支持標準Modbus TCP&#xff0c;可集成到SCADA、O…

Spring STOMP-連接到消息代理

STOMP 代理中繼維護一個與消息代理的“系統”TCP 連接。這個連接僅用于來自服務器端應用程序的消息&#xff0c;不用于接收消息。您可以為此連接配置STOMP憑據&#xff08;即STOMP幀的login和passcode頭部&#xff09;。這在XML命名空間和Java配置中都以systemLogin和systemPas…

CentOs搭建Kubernetes集群

kubeadm minikube 還是太“迷你”了&#xff0c;方便的同時也隱藏了很多細節&#xff0c;離真正生產環境里的計算集群有一些差距&#xff0c;畢竟許多需求、任務只有在多節點的大集群里才能夠遇到&#xff0c;相比起來&#xff0c;minikube 真的只能算是一個“玩具”。 Kuber…

spring基礎使用(案例)

基于xml使用&#xff1a; 準備&#xff1a; 1.Dao層&#xff08;接口&#xff09;&#xff1a; public interface UserDao {public void save(); } 1.1 Dao層&#xff08;實現類&#xff09;&#xff1a; public class UserDaoIim implements UserDao {Overridepublic vo…

Day53代碼隨想錄動態規劃part13:300.最長遞增子序列、674. 最長連續遞增序列、718. 最長重復子數組

Day52 動態規劃part13 300.最長遞增子序列 leetcode鏈接&#xff1a;300. 最長遞增子序列 - 力扣&#xff08;LeetCode&#xff09; 題意&#xff1a;給你一個整數數組 nums &#xff0c;找到其中最長嚴格遞增子序列的長度。子序列是由數組派生而來的序列&#xff0c;刪除&a…

23種設計模式(軟考中級 軟件設計師)

設計模式 23個設計模式&#xff0c;23個意圖 1. 設計模式概要 設計模式的核心在于提供了相關問題的解決方案&#xff0c;使得人們可以更加簡單方便的復用成功的設計和體系結構 設計模式的類別 創建型結構型行為型類工廠方法模式適配器模式&#xff08;類&#xff09;解釋器模…

物聯網五層架構分析

物聯網五層架構分析 隨著科技的迅速發展&#xff0c;物聯網&#xff08;IoT&#xff09;作為日常生活中不可或缺的一部分&#xff0c;已融入人們的生活和工作中。物聯網五層架構&#xff0c;包括感知層、網絡層、數據層、應用層和業務層&#xff0c;扮演著關鍵的角色。 感知層 …

網絡庫-libcurl介紹

1.簡介 libcurl 是一個功能強大的庫&#xff0c;支持多種協議&#xff0c;用于數據傳輸。它廣泛應用于實現網絡操作&#xff0c;如HTTP、HTTPS、FTP、FTPS、SCP、SFTP等。libcurl 提供了豐富的 API&#xff0c;可以在多種編程語言中使用。 libcurl 主要特點 支持多種協議&am…

FreeRTOS計數型信號量

目錄 一、計數型信號量簡介 二、計數型信號量相關API 1、創建計數型信號量 2、釋放計數型信號量 3、獲取計數型信號量 4、獲取計數型信號量的計數值 三、計數型信號量實操 1、實驗需求 2、CubeMX配置 3、代碼實現 一、計數型信號量簡介 ①取值只有0與1兩種狀態的信號…

基于Springboot的滴答拍攝影

基于SpringbootVue的滴答拍攝影設計與實現 開發語言&#xff1a;Java數據庫&#xff1a;MySQL技術&#xff1a;SpringbootMybatis工具&#xff1a;IDEA、Maven、Navicat 系統展示 用戶登錄 首頁 攝影作品 攝影服務 攝影論壇 后臺登錄 后臺首頁 用戶管理 攝影師管理 攝影作…

YOLOv8小白中的小白安裝環境教程!沒一個字廢話,看一遍不踩坑!

文章目錄 去哪里下代碼&#xff1f;怎么下代碼&#xff1f;怎么裝環境&#xff1f;命令行界面(CLI)指令和Python腳本區別&#xff1f;附錄1 conda常用指令附錄2 git常用指令附錄3 項目代碼文件作用 去哪里下代碼&#xff1f; 下載代碼請大家直接去 YOLOv8的官方倉庫下載&#…

HTTP和HTTPS的區別和聯系

目錄 1. 簡介2. TLS 握手過程3. 常見的加密算法3.1 對稱加密算法3.2 非對稱加密算法 1. 簡介 HTTPS在HTTP的基礎上引入了一個TLS層&#xff0c;采用密文進行傳輸&#xff0c;結合對稱加密技術和非對稱加密技術來實現數據的安全性和完整性。 客戶端會生成隨機密鑰&#xff0c;…

讓 計算機 將 數學 公式 表達式 的計算過程繪制出來 【mathematical-expression(MAE)】

目錄 文章目錄 目錄介紹開始實戰引入數學表達式計算庫引入流程圖代碼生成庫開始進行生成 介紹 大家好 今天我們來分享一個新知識&#xff0c;將數學表達式的整個計算過程&#xff0c;以及計算繁多結果在 Java 中繪制出來&#xff0c;計算機中的數學表達式計算的功能很常見了&a…

react 對輸入做出反應與狀態

React 提供了一種操作 UI 的聲明性方式。您無需直接操作 UI 的各個部分&#xff0c;而是描述組件可能處于的不同狀態&#xff0c;并在它們之間切換以響應用戶輸入。 聲明式 UI 與命令式 UI 的比較 在設計 UI 交互時&#xff0c;可能會考慮 UI 如何響應用戶操作而更改。考慮一…