跳到主要内容纯 Java 实现的个人所得税计算模拟器源码 | 极客日志JavaPayjava算法
纯 Java 实现的个人所得税计算模拟器源码
个人所得税计算模拟器基于 Java Swing 开发,模拟个税 APP 核心功能。包含综合所得年度汇算、税率表查询及专项扣除设置。采用 BigDecimal 确保计算精度,遵循 2023 年最新个税政策。提供完整 GUI 界面与核心计算逻辑,支持输入收入、专项扣除及附加扣除后自动计算应纳税额与税后收入。适用于 Java 学习及税务计算参考,代码结构清晰,无第三方依赖。
AiEngineer19 浏览 纯 Java 实现的个人所得税计算模拟器源码
一、项目简介
这是一个使用 Java Swing 开发的个人所得税计算模拟器,模拟了官方个税 APP 的核心功能,包括:
- 综合所得年度汇算计算
- 税率表查询
- 专项扣除项目设置
- 税务计算结果展示
项目特点:
- 100% 纯 Java 实现,无第三方依赖
- 完整 GUI 界面,支持用户交互
- 详细的代码注释
- 遵循 2023 年最新个税政策
二、核心代码实现
1. 主程序入口
package com.tax.calculator;
import javax.swing.*;
public class PersonalIncomeTaxApp {
public static void main(String[] args) {
SwingUtilities.invokeLater(() -> {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
TaxCalculatorFrame frame = new TaxCalculatorFrame();
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setVisible(true);
System.out.println("个人所得税计算模拟器启动成功!");
} catch (Exception e) {
e.printStackTrace();
JOptionPane.showMessageDialog(null,
"程序启动失败:" + e.getMessage(),
"错误",
JOptionPane.ERROR_MESSAGE);
}
});
}
}
2. 个税计算核心类
package com.tax.calculator;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.HashMap;
import java.util.Map;
public class TaxCalculator {
private static final TaxBracket[] TAX_BRACKETS = {
new TaxBracket(0, 36000, 0.03, 0),
new TaxBracket(36000, 144000, 0.10, 2520),
new TaxBracket(144000, 300000, 0.20, 16920),
new TaxBracket(300000, 420000, 0.25, 31920),
new TaxBracket(420000, 660000, 0.30, 52920),
new TaxBracket(660000, 960000, 0.35, 85920),
new TaxBracket(960000, Double.MAX_VALUE, 0.45, 181920)
};
private static final Map<String, BigDecimal> SPECIAL_DEDUCTIONS = new HashMap<>();
static {
SPECIAL_DEDUCTIONS.put("养老", new BigDecimal("1000"));
SPECIAL_DEDUCTIONS.put("医疗", new BigDecimal("200"));
SPECIAL_DEDUCTIONS.put("失业", new BigDecimal("50"));
SPECIAL_DEDUCTIONS.put("住房", new BigDecimal("1200"));
SPECIAL_DEDUCTIONS.put("子女教育", new BigDecimal("1000"));
SPECIAL_DEDUCTIONS.put("继续教育", new BigDecimal("400"));
SPECIAL_DEDUCTIONS.put("大病医疗", new BigDecimal("8000"));
SPECIAL_DEDUCTIONS.put("房贷利息", new BigDecimal("1000"));
SPECIAL_DEDUCTIONS.put("住房租金", new BigDecimal("1500"));
SPECIAL_DEDUCTIONS.put("赡养老人", new BigDecimal("2000"));
}
public static TaxResult calculateAnnualTax(
double annualIncome,
double specialDeductions,
double additionalDeductions) {
final double BASIC_DEDUCTION = 60000;
BigDecimal income = BigDecimal.valueOf(annualIncome);
BigDecimal special = BigDecimal.valueOf(specialDeductions);
BigDecimal additional = BigDecimal.valueOf(additionalDeductions);
BigDecimal basic = BigDecimal.valueOf(BASIC_DEDUCTION);
BigDecimal taxableIncome = income
.subtract(special)
.subtract(additional)
.subtract(basic)
.max(BigDecimal.ZERO);
TaxBracket bracket = findTaxBracket(taxableIncome.doubleValue());
BigDecimal taxAmount = taxableIncome
.multiply(BigDecimal.valueOf(bracket.getRate()))
.subtract(BigDecimal.valueOf(bracket.getQuickDeduction()));
taxAmount = taxAmount.max(BigDecimal.ZERO);
BigDecimal afterTaxIncome = income.subtract(taxAmount);
return new TaxResult(
income.doubleValue(),
taxableIncome.doubleValue(),
taxAmount.doubleValue(),
afterTaxIncome.doubleValue(),
bracket
);
}
private static TaxBracket findTaxBracket(double taxableIncome) {
for (TaxBracket bracket : TAX_BRACKETS) {
if (taxableIncome >= bracket.getLowerBound() &&
taxableIncome < bracket.getUpperBound()) {
return bracket;
}
}
return TAX_BRACKETS[TAX_BRACKETS.length - 1];
}
public static Map<String, BigDecimal> getSpecialDeductionStandards() {
return new HashMap<>(SPECIAL_DEDUCTIONS);
}
public static class TaxBracket {
private final double lowerBound;
private final double upperBound;
private final double rate;
private final double quickDeduction;
public TaxBracket(double lowerBound, double upperBound,
double rate, double quickDeduction) {
this.lowerBound = lowerBound;
this.upperBound = upperBound;
this.rate = rate;
this.quickDeduction = quickDeduction;
}
public double getLowerBound() { return lowerBound; }
public double getUpperBound() { return upperBound; }
public double getRate() { return rate; }
public double getQuickDeduction() { return quickDeduction; }
@Override
public String toString() {
return String.format("税率:%.1f%%, 速算扣除数:%.0f", rate * 100, quickDeduction);
}
}
public static class TaxResult {
private final double totalIncome;
private final double taxableIncome;
private final double taxAmount;
private final double afterTaxIncome;
private final TaxBracket taxBracket;
public TaxResult(double totalIncome, double taxableIncome,
double taxAmount, double afterTaxIncome,
TaxBracket taxBracket) {
this.totalIncome = totalIncome;
this.taxableIncome = taxableIncome;
this.taxAmount = taxAmount;
this.afterTaxIncome = afterTaxIncome;
this.taxBracket = taxBracket;
}
public double getTotalIncome() { return totalIncome; }
public double getTaxableIncome() { return taxableIncome; }
public double getTaxAmount() { return taxAmount; }
public double getAfterTaxIncome() { return afterTaxIncome; }
public TaxBracket getTaxBracket() { return taxBracket; }
@Override
public String toString() {
return String.format(
"计算结果:\n" +
"总收入:¥%.2f\n" +
"应纳税所得额:¥%.2f\n" +
"应纳税额:¥%.2f\n" +
"税后收入:¥%.2f\n" +
"适用税率:%s",
totalIncome, taxableIncome, taxAmount, afterTaxIncome, taxBracket
);
}
}
}
3. GUI 界面实现
package com.tax.calculator;
import javax.swing.*;
import javax.swing.border.TitledBorder;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.math.BigDecimal;
import java.util.Map;
public class TaxCalculatorFrame extends JFrame {
private JTextField incomeField;
private JTextField specialDeductionField;
private JTextField additionalDeductionField;
private JTextArea resultArea;
private JComboBox<String> deductionTypeCombo;
private JLabel standardLabel;
public TaxCalculatorFrame() {
initUI();
initData();
}
private void initUI() {
setTitle("个人所得税计算模拟器 v1.0");
setSize(800, 600);
setLocationRelativeTo(null);
JPanel mainPanel = new JPanel(new BorderLayout(10, 10));
mainPanel.setBorder(BorderFactory.createEmptyBorder(10, 10, 10, 10));
mainPanel.add(createInputPanel(), BorderLayout.NORTH);
mainPanel.add(createResultPanel(), BorderLayout.CENTER);
mainPanel.add(createButtonPanel(), BorderLayout.SOUTH);
add(mainPanel);
}
private JPanel createInputPanel() {
JPanel panel = new JPanel(new GridLayout(5, 2, 10, 10));
panel.setBorder(BorderFactory.createTitledBorder(
BorderFactory.createLineBorder(Color.GRAY),
"个税计算参数输入",
TitledBorder.LEFT,
TitledBorder.TOP
));
panel.add(new JLabel("年度总收入 (¥):"));
incomeField = new JTextField("120000");
panel.add(incomeField);
panel.add(new JLabel("三险一金专项扣除 (¥):"));
specialDeductionField = new JTextField("10000");
panel.add(specialDeductionField);
panel.add(new JLabel("专项附加扣除 (¥):"));
additionalDeductionField = new JTextField("3000");
panel.add(additionalDeductionField);
panel.add(new JLabel("扣除项目查询:"));
JPanel queryPanel = new JPanel(new FlowLayout(FlowLayout.LEFT));
deductionTypeCombo = new JComboBox<>();
queryPanel.add(deductionTypeCombo);
standardLabel = new JLabel("标准:¥0");
queryPanel.add(standardLabel);
panel.add(queryPanel);
return panel;
}
private JScrollPane createResultPanel() {
resultArea = new JTextArea();
resultArea.setEditable(false);
resultArea.setFont(new Font("宋体", Font.PLAIN, 14));
resultArea.setBorder(BorderFactory.createEmptyBorder(10, 10, 10, 10));
JScrollPane scrollPane = new JScrollPane(resultArea);
scrollPane.setBorder(BorderFactory.createTitledBorder("计算结果"));
return scrollPane;
}
private JPanel createButtonPanel() {
JPanel panel = new JPanel(new FlowLayout(FlowLayout.CENTER, 20, 10));
JButton calculateBtn = new JButton("计算个税");
calculateBtn.setFont(new Font("微软雅黑", Font.BOLD, 14));
calculateBtn.setBackground(new Color(70, 130, 180));
calculateBtn.setForeground(Color.WHITE);
calculateBtn.setPreferredSize(new Dimension(120, 40));
calculateBtn.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
calculateTax();
}
});
JButton clearBtn = new JButton("清除结果");
clearBtn.setFont(new Font("微软雅黑", Font.PLAIN, 14));
clearBtn.setPreferredSize(new Dimension(120, 40));
clearBtn.addActionListener(e -> clearResults());
JButton rateTableBtn = new JButton("查看税率表");
rateTableBtn.setFont(new Font("微软雅黑", Font.PLAIN, 14));
rateTableBtn.setPreferredSize(new Dimension(120, 40));
rateTableBtn.addActionListener(e -> showTaxRateTable());
panel.add(calculateBtn);
panel.add(clearBtn);
panel.add(rateTableBtn);
return panel;
}
private void initData() {
Map<String, BigDecimal> standards = TaxCalculator.getSpecialDeductionStandards();
for (String key : standards.keySet()) {
deductionTypeCombo.addItem(key);
}
deductionTypeCombo.addActionListener(e -> {
String selected = (String) deductionTypeCombo.getSelectedItem();
if (selected != null) {
BigDecimal standard = standards.get(selected);
standardLabel.setText(String.format("标准:¥%.2f", standard));
}
});
if (deductionTypeCombo.getItemCount() > 0) {
deductionTypeCombo.setSelectedIndex(0);
}
}
private void calculateTax() {
try {
double income = Double.parseDouble(incomeField.getText());
double special = Double.parseDouble(specialDeductionField.getText());
double additional = Double.parseDouble(additionalDeductionField.getText());
if (income < 0 || special < 0 || additional < 0) {
JOptionPane.showMessageDialog(this,
"输入值不能为负数!",
"输入错误",
JOptionPane.WARNING_MESSAGE);
return;
}
TaxCalculator.TaxResult result = TaxCalculator.calculateAnnualTax(
income, special, additional);
displayResult(result);
} catch (NumberFormatException ex) {
JOptionPane.showMessageDialog(this,
"请输入有效的数字!",
"输入错误",
JOptionPane.ERROR_MESSAGE);
}
}
private void displayResult(TaxCalculator.TaxResult result) {
StringBuilder sb = new StringBuilder();
sb.append("=== 个人所得税计算结果 ===\n\n");
sb.append(String.format("年度总收入:¥%,.2f\n", result.getTotalIncome()));
sb.append(String.format("应纳税所得额:¥%,.2f\n", result.getTaxableIncome()));
sb.append(String.format("适用税率档次:%s\n", result.getTaxBracket()));
sb.append(String.format("应纳个人所得税:¥%,.2f\n", result.getTaxAmount()));
sb.append(String.format("年度税后收入:¥%,.2f\n\n", result.getAfterTaxIncome()));
double monthlyTax = result.getTaxAmount() / 12;
double monthlyAfterTax = result.getAfterTaxIncome() / 12;
sb.append("=== 月度数据估算 ===\n");
sb.append(String.format("月度平均纳税:¥%,.2f\n", monthlyTax));
sb.append(String.format("月度税后收入:¥%,.2f\n\n", monthlyAfterTax));
sb.append("=== 税务优化建议 ===\n");
if (result.getTaxableIncome() > 0) {
sb.append("1. 充分利用专项附加扣除项目\n");
sb.append("2. 合理规划年度收入时间分布\n");
sb.append("3. 符合条件的捐赠可税前扣除\n");
} else {
sb.append("当前收入无需缴纳个人所得税\n");
}
resultArea.setText(sb.toString());
resultArea.setCaretPosition(0);
}
private void showTaxRateTable() {
StringBuilder sb = new StringBuilder();
sb.append("=== 个人所得税税率表(综合所得) ===\n\n");
sb.append("级数 | 全年应纳税所得额 | 税率 | 速算扣除数\n");
sb.append("----|-----------------|------|----------\n");
TaxCalculator.TaxBracket[] brackets = new TaxCalculator.TaxBracket[]{
new TaxCalculator.TaxBracket(0, 36000, 0.03, 0),
new TaxCalculator.TaxBracket(36000, 144000, 0.10, 2520),
new TaxCalculator.TaxBracket(144000, 300000, 0.20, 16920),
new TaxCalculator.TaxBracket(300000, 420000, 0.25, 31920),
new TaxCalculator.TaxBracket(420000, 660000, 0.30, 52920),
new TaxCalculator.TaxBracket(660000, 960000, 0.35, 85920),
new TaxCalculator.TaxBracket(960000, Double.MAX_VALUE, 0.45, 181920)
};
for (int i = 0; i < brackets.length; i++) {
TaxCalculator.TaxBracket b = brackets[i];
String range;
if (b.getUpperBound() == Double.MAX_VALUE) {
range = String.format("超过%,.0f 元", b.getLowerBound());
} else {
range = String.format("%,.0f - %,.0f 元",
b.getLowerBound(), b.getUpperBound());
}
sb.append(String.format("%-4d| %-15s | %.1f%% | %,.0f 元\n",
i + 1, range, b.getRate() * 100, b.getQuickDeduction()));
}
sb.append("\n注:应纳税所得额 = 年度收入 - 6 万元 (基本扣除) - 专项扣除 - 专项附加扣除\n");
resultArea.setText(sb.toString());
}
private void clearResults() {
resultArea.setText("");
}
}
三、使用说明
1. 运行环境要求
- Java 8 或更高版本
- 支持 Swing 的桌面环境
2. 编译运行
javac -d . com/tax/calculator/*.java
java com.tax.calculator.PersonalIncomeTaxApp
3. 程序功能演示
- 输入计算参数:
- 查询扣除标准:
- 计算个税:
- 查看税率表:
四、核心算法说明
1. 计算公式
应纳税所得额 = 年度收入 - 60000(基本减除费用) - 专项扣除 - 专项附加扣除
应纳税额 = 应纳税所得额 × 适用税率 - 速算扣除数
2. 税率表算法
五、项目扩展建议
- 数据持久化:添加文件保存/加载功能
- 历史记录:记录多次计算结果
- 导出功能:支持 PDF/Excel 导出
- 联网更新:自动更新税率政策
- 图表展示:使用 JFreeChart 添加图表
六、注意事项
- 本程序为模拟器,实际报税请以官方系统为准
- 税率政策如有更新,需要相应修改代码
- 计算结果仅供参考,不构成税务建议
七、开源协议
本项目采用 MIT 开源协议,允许自由使用、修改和分发。
八、运行截图
由于无法在本文中直接显示图片,以下是程序运行效果描述:
- 主界面:包含输入区、结果显示区和功能按钮
- 计算结果:详细展示各项税务数据
- 税率表:完整的 7 级累进税率表
相关免费在线工具
- Keycode 信息
查找任何按下的键的javascript键代码、代码、位置和修饰符。 在线工具,Keycode 信息在线工具,online
- Escape 与 Native 编解码
JavaScript 字符串转义/反转义;Java 风格 \uXXXX(Native2Ascii)编码与解码。 在线工具,Escape 与 Native 编解码在线工具,online
- JavaScript / HTML 格式化
使用 Prettier 在浏览器内格式化 JavaScript 或 HTML 片段。 在线工具,JavaScript / HTML 格式化在线工具,online
- JavaScript 压缩与混淆
Terser 压缩、变量名混淆,或 javascript-obfuscator 高强度混淆(体积会增大)。 在线工具,JavaScript 压缩与混淆在线工具,online
- 加密/解密文本
使用加密算法(如AES、TripleDES、Rabbit或RC4)加密和解密文本明文。 在线工具,加密/解密文本在线工具,online
- Gemini 图片去水印
基于开源反向 Alpha 混合算法去除 Gemini/Nano Banana 图片水印,支持批量处理与下载。 在线工具,Gemini 图片去水印在线工具,online