java快速学习速查(2)
高速通过中ing……
本篇为变量类型,变量命名规则,修饰符,运算符
Java变量类型全面解析
变量是Java程序中最基本的存储单元,理解不同类型的变量及其特性是Java编程的基础。下面我将从实际开发角度,深入讲解Java中的各种变量类型。
一、变量类型体系
1 2 3 4 5 6 7 8 9 10 11 12
   | Java变量类型 ├── 按声明位置分 │   ├── 成员变量(类中声明) │   │   ├── 实例变量(非static) │   │   └── 类变量(static) │   └── 局部变量(方法/块中声明) │       ├── 方法局部变量 │       ├── 代码块变量 │       └── 参数变量 └── 按数据类型分     ├── 基本类型变量     └── 引用类型变量
   | 
 
二、局部变量详解
1. 核心特性
- 作用域:仅在声明它的方法/代码块内有效
 
- 生命周期:方法/块开始执行时创建,执行结束时销毁
 
- 存储位置:栈内存
 
- 初始化要求:必须显式初始化后才能使用
 
2. 使用示例
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
   | public class LocalVarDemo {     public void calculate() {                  int result = 0;           for(int i=0; i<10; i++) {               result += i;         }                       }          public static void main(String[] args) {                  if(args.length > 0) {             String message = "参数存在";               System.out.println(message);         }              } }
  | 
 
3. 关键注意事项
- 局部变量不能使用
static修饰 
- 不同代码块中可以声明同名局部变量
 
- 方法参数本质也是局部变量
 
三、成员变量(实例变量)深度解析
1. 核心特性
- 作用域:整个类内部(不同访问修饰符影响外部可见性)
 
- 生命周期:对象创建时初始化,对象被GC回收时销毁
 
- 存储位置:堆内存(作为对象的一部分)
 
- 初始化:自动赋予默认值(可显式初始化)
 
2. 默认值规则
| 数据类型 | 
默认值 | 
| byte/short/int/long | 
0 | 
| float/double | 
0.0 | 
| char | 
‘\u0000’ | 
| boolean | 
false | 
| 引用类型 | 
null | 
 
3. 使用示例
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21
   | public class Student {          private String name;         private int age;             private boolean graduated;           public Student(String name, int age) {         this.name = name;            this.age = age;     }          public void graduate() {         graduated = true;            int localVar = 2023;      }          public void printInfo() {         System.out.println(name + ":" + age + "岁," +                            (graduated ? "已毕业" : "在读"));     } }
  | 
 
4. 最佳实践
- 通常设为
private,通过getter/setter访问 
- 重要变量应在构造器中初始化
 
- 避免过多的公有实例变量
 
四、类变量(静态变量)全面剖析
1. 核心特性
- 作用域:整个类(可通过类名直接访问)
 
- 生命周期:类加载时初始化,程序结束时销毁
 
- 存储位置:方法区(JDK8+的元空间)
 
- 共享性:所有类实例共享同一份数据
 
2. 使用示例
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28
   | public class Employee {          private String id;     private String name;               private static int nextId = 1;       public static final String COMPANY = "ABC科技";           public Employee(String name) {         this.id = "EMP" + String.format("%04d", nextId++);         this.name = name;     }          public static int getNextId() {         return nextId;       }          public static void main(String[] args) {         System.out.println("公司:" + Employee.COMPANY);         Employee e1 = new Employee("张三");         Employee e2 = new Employee("李四");                  System.out.println(e1.id);           System.out.println(e2.id);           System.out.println("下一个ID:" + Employee.getNextId());      } }
  | 
 
3. 关键注意事项
- 静态变量不属于任何对象实例
 
- 静态方法只能直接访问静态成员
 
- 多线程环境下需要考虑线程安全
 
- 静态常量命名推荐全大写+下划线
 
五、参数变量特殊机制
1. 值传递与引用传递
- 基本类型:值传递(传递副本)
 
- 引用类型:引用值传递(传递引用的副本)
 
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19
   | public class ParamDemo {     public static void modify(int num, String str, int[] arr) {         num = 100;         str = "修改后";         arr[0] = 99;     }          public static void main(String[] args) {         int n = 1;         String s = "原始";         int[] a = {1, 2, 3};                  modify(n, s, a);                  System.out.println(n);           System.out.println(s);           System.out.println(Arrays.toString(a));      } }
  | 
 
2. 可变参数
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
   | public class VarargsDemo {     public static double average(int... numbers) {         if(numbers.length == 0) return 0;         int sum = 0;         for(int num : numbers) {             sum += num;         }         return (double)sum / numbers.length;     }          public static void main(String[] args) {         System.out.println(average(1, 2, 3));              System.out.println(average(5, 10, 15, 20));      } }
  | 
 
六、变量对比总结表
| 特性 | 
局部变量 | 
实例变量 | 
类变量 | 
| 声明位置 | 
方法/块内部 | 
类中方法外 | 
类中方法外+static | 
| 初始化要求 | 
必须显式初始化 | 
自动初始化 | 
自动初始化 | 
| 默认值 | 
无(必须初始化) | 
有(各类型默认值) | 
有(同实例变量) | 
| 作用域 | 
声明块内部 | 
整个类 | 
整个类 | 
| 生命周期 | 
方法/块执行期间 | 
对象存在期间 | 
程序运行期间 | 
| 存储位置 | 
栈内存 | 
堆内存(对象内) | 
方法区 | 
| 访问方式 | 
直接访问 | 
对象.变量名 | 
类名.变量名 | 
| 线程安全 | 
天然线程安全 | 
不安全 | 
不安全 | 
| 共享性 | 
不共享 | 
对象间不共享 | 
全局共享 | 
 
七、变量使用最佳实践
1. 命名规范
- 遵循驼峰命名法(局部/实例变量小写开头,类变量全大写)
 
- 见名知意(避免单字符命名,除临时变量)
 
- 避免使用$和_开头
 
2. 作用域最小化
- 尽量缩小变量作用域(优先使用局部变量)
 
- 避免不必要的成员变量
 
3. 初始化策略
- 局部变量:声明时立即初始化
 
- 实例变量:构造器中初始化关键变量
 
- 类变量:静态代码块中初始化复杂静态变量
 
4. 线程安全考虑
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
   | public class Counter {          private static int count1 = 0;               private static volatile int count2 = 0;               private static AtomicInteger count3 = new AtomicInteger(0);               private static int count4 = 0;     public static synchronized void increment() {         count4++;     } }
  | 
 
八、典型面试问题解析
问题1:以下代码输出什么?
1 2 3 4 5 6 7 8 9 10 11 12 13
   | public class VariableQuiz {     static int x = 10;     int y = 20;          public static void main(String[] args) {         VariableQuiz v1 = new VariableQuiz();         v1.x = 100;         v1.y = 200;                  VariableQuiz v2 = new VariableQuiz();         System.out.println(v2.x + " " + v2.y);     } }
  | 
 
答案:输出”100 20”。因为x是静态变量被所有实例共享,y是实例变量每个对象独立。
问题2:为什么局部变量必须初始化?
解析:Java设计者为了避免因未初始化变量导致的不可预测行为。成员变量有默认值是为了对象创建的合理性,而局部变量作用域小,强制初始化能减少错误。
问题3:以下哪种变量线程安全?
A. 局部变量
B. 实例变量
C. 静态变量
答案:A。局部变量存储在栈中,每个线程有自己的栈空间。
Java变量命名规范深度解析
良好的命名规范是编写可读性强、可维护性高的Java代码的基础。下面我将全面系统地讲解Java中各类变量的命名规则和最佳实践。
一、命名基础规则
1. 通用命名原则
- 合法字符:字母、数字、下划线和美元符号($)
 
- 开头限制:不能以数字开头
 
- 长度限制:理论上无限制,但建议不超过50个字符
 
- 大小写敏感:
myVar和myvar是不同的变量 
- 关键字规避:不能使用Java保留字(如
class, int等) 
2. 命名风格对比
| 命名风格 | 
示例 | 
适用场景 | 
| 小驼峰(lowerCamel) | 
studentName | 
变量、方法名 | 
| 大驼峰(UpperCamel) | 
StudentService | 
类名、接口名 | 
| 蛇形(SNAKE_CASE) | 
MAX_VALUE | 
常量 | 
| 匈牙利(不推荐) | 
strFirstName | 
旧代码(现代Java不推荐) | 
 
二、具体变量类型命名规范
1. 局部变量命名
- 规则:小驼峰,简短且描述性
 
- 示例:
1 2 3 4 5 6 7 8
   | int itemCount = 0; String customerName = "张三"; double totalPrice = calculateTotal();
 
  for(int i=0; i<10; i++) {      }
   | 
 
 
2. 实例变量命名
- 规则:小驼峰,反映对象状态
 
- 示例:
1 2 3 4 5 6 7 8
   | public class Student {     private String studentId;         private boolean isGraduated;      protected String major;                     private boolean hasScholarship; }
  | 
 
 
3. 静态变量命名
- 规则:
 
- 示例:
1 2 3 4 5 6 7 8
   | public class Config {          private static int instanceCount = 0;               public static final int MAX_CONNECTIONS = 100;     public static final String DEFAULT_ENCODING = "UTF-8"; }
  | 
 
 
4. 参数变量命名
- 规则:小驼峰,明确表达参数用途
 
- 示例:
1 2 3 4 5 6 7 8
   | public void registerUser(String userName, String passwordHash) {      }
 
  public void setActive(boolean isActive) {      }
  | 
 
 
5. 泛型类型参数
泛型一般放在<>中,在定义类或方法时使用。限定传入值的类型
- 规则:单个大写字母,常用约定:
E - 集合元素 
K - 键 
V - 值 
T - 类型 
S, U - 第二、第三类型 
 
- 示例:
1 2 3 4 5 6 7 8 9 10 11 12
   | public class Box<T> {     private T content;          public void setContent(T content) {         this.content = content;     } }
  public interface Map<K, V> {     V get(K key);      }
  | 
 
自定义泛型类:1 2 3 4 5
   | public class MyList<T> {     private T[] items;     private int size;      }
  | 
 
自定义泛型方法:1 2 3 4 5
   | public <T> void printArray(T[] array) {     for (T item : array) {         System.out.println(item);     } }
  | 
 
泛型方法的类型参数通常放在返回值之前。 
三、特殊场景命名规范
1. 集合类型变量
- 推荐后缀:List/Set/Map等类型指示
 
- 示例:
1 2 3
   | List<String> studentNameList = new ArrayList<>(); Map<Integer, Student> studentIdMap = new HashMap<>(); Set<Course> requiredCourseSet = new HashSet<>();
   | 
 
 
2. 布尔类型变量
- 推荐前缀:
is - 状态标识 
has - 拥有关系 
can - 能力判断 
should - 条件判断 
 
- 示例:
1 2 3 4
   | private boolean isActive; private boolean hasLicense; private boolean canEdit; private boolean shouldValidate;
   | 
 
 
3. 测试代码命名
- 方法名:可使用下划线增强可读性
 
- 示例:
1 2 3 4 5 6 7 8 9
   | @Test public void isAdult_AgeOver18_ReturnsTrue() {      }
  @Test public void calculatePrice_WithDiscount_AppliesDiscount() {      }
   | 
 
 
四、命名禁忌与常见错误
1. 绝对避免的命名
1 2 3 4 5 6 7 8 9 10 11 12
   |  int a = 10;   String temp = "value";
 
  List<String> name = new ArrayList<>();  
 
  String UserName;  
 
  int 2ndPlace;  
 
  | 
 
2. 不推荐的命名实践
1 2 3 4 5 6 7 8 9 10
   |  String strName;   int iCount;
 
  String theNameOfTheStudentWhoIsTakingTheAdvancedJavaCourse;
 
  int custCnt;   int usrNum;   
 
  | 
 
五、行业标准参考
1. 官方规范
2. 常用框架命名示例
Spring示例:
1 2 3 4 5 6 7 8 9
   | @Repository public class UserDaoImpl implements UserDao {     private final JdbcTemplate jdbcTemplate;          @Autowired     public UserDaoImpl(DataSource dataSource) {         this.jdbcTemplate = new JdbcTemplate(dataSource);     } }
   | 
JUnit测试示例:
1 2 3 4 5 6
   | public class StringUtilsTest {     @Test     public void isEmpty_WhenNullInput_ReturnsTrue() {         assertTrue(StringUtils.isEmpty(null));     } }
  | 
六、命名检查工具
1. Checkstyle配置示例
1 2 3 4 5 6 7 8 9 10 11
   | <module name="LocalVariableName">     <property name="format" value="^[a-z][a-zA-Z0-9]*$"/> </module>
  <module name="MemberName">     <property name="format" value="^[a-z][a-zA-Z0-9]*$"/> </module>
  <module name="ConstantName">     <property name="format" value="^[A-Z][A-Z0-9]*(_[A-Z0-9]+)*$"/> </module>
   | 
 
2. IDE模板设置
- IntelliJ IDEA:
File → Settings → Editor → Code Style → Java 
- Eclipse:
Window → Preferences → Java → Code Style → Formatter 
七、命名重构技巧
1. 重命名快捷键
- IntelliJ:Shift+F6
 
- Eclipse:Alt+Shift+R
 
2. 批量重命名示例
1 2 3 4 5 6 7
   |  int d;   d = 5;
 
  int daysUntilExpiration; daysUntilExpiration = 5;
 
  | 
 
3. 命名重构原则
- 见名知意:名称应准确表达变量用途
 
- 避免歧义:如
accountList如果不是List类型就不要用 
- 保持一致性:整个项目使用相同的命名风格
 
- 适度缩写:如
num代替number可以接受,但避免过度缩写 
八、典型场景命名示例
1. 计数器变量
1 2 3 4 5
   |  int failedAttemptCount = 0;
 
  int counter = 0;
 
  | 
 
2. 临时变量
1 2 3 4 5 6 7 8
   |  public void processOrder(Order order) {          double discountedPrice = calculateDiscountedPrice(order);               double temp = calculateDiscountedPrice(order); }
 
  | 
 
3. 状态标志
1 2 3 4 5 6 7
   |  boolean isConnected = false; boolean hasPermission = true;
 
  boolean flag = false; boolean status = true;
 
  | 
 
Java修饰符全面解析
修饰符是Java语言中用于控制类、变量、方法等元素访问权限和行为特性的关键字。下面我将系统性地讲解Java中的各种修饰符及其应用场景。
一、访问修饰符详解
1. 访问控制级别对比
| 修饰符 | 
类内部 | 
同包 | 
不同包子类 | 
不同包非子类 | 
适用对象 | 
| public | 
✓ | 
✓ | 
✓ | 
✓ | 
类、接口、变量、方法 | 
| protected | 
✓ | 
✓ | 
✓ | 
× | 
变量、方法、内部类 | 
| default | 
✓ | 
✓ | 
× | 
× | 
类、接口、变量、方法 | 
| private | 
✓ | 
× | 
× | 
× | 
变量、方法、构造器、内部类 | 
 
public具有最大权限,private具有最小权限。
访问修饰符使用原则
1.一般情况使用public修饰符
2.如果希望类的成员仅在当前类可见,使用private修饰符
3.如果希望类的成员仅在当前包可见,不使用任何修饰符
4.如果希望类的成员仅在当前包和子类可见,使用protected修饰符
2. public修饰符应用
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19
   |  public class Animal {          public String name;               public void eat() {         System.out.println(name + " is eating");     }               public Animal(String name) {         this.name = name;     } }
 
 
 
 
 
  | 
 
3. protected修饰符实战
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30
   | package com.example;
  public class Vehicle {     protected String brand;            protected void startEngine() {         System.out.println(brand + " engine starting");     } }
 
  class Garage {     void repair(Vehicle v) {         v.startEngine();       } }
 
  package com.test; import com.example.Vehicle;
  class Car extends Vehicle {     void demo() {         brand = "Toyota";           startEngine();                                     } }
   | 
 
4. 默认(default)修饰符示例
1 2 3 4 5 6 7
   | class PackagePrivateClass {       int count;                        void increment() {         count++;     } }
  | 
 
5. private修饰符最佳实践
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21
   | public class BankAccount {          private double balance;     private String accountNumber;               public double getBalance() {         return balance;     }               private boolean isValidAmount(double amount) {         return amount > 0;     }          public void deposit(double amount) {         if(isValidAmount(amount)) {             balance += amount;         }     } }
  | 
 
二、非访问修饰符深度解析
1. static修饰符
如果属性或者方法被static修饰符,表示这个属性与方法不再属于对象,而是属性整个类,它会被多个
对象共享。被static关键字修饰的不需要去创建对象去调用,直接根据类名就可以去访问,也就是说方
便再没有创建对象的情况下来进行调用。
修饰属性
被static修饰的成员变量叫做静态变量,也叫做类变量,说明这个变量是属性这个类的,而不是属于对象。没有被static修饰符的成员变量,说明这个变量是属性具体的对象的。
修饰方法
被static修饰符的方法叫做静态方法,说明这个方法是属于这个类的,而不是属于对象,没有被static修饰的成员方法,说明这个方法是属于具体的对象的。
注意事项
1.静态的可以访问静态,但不能访问非静态的。
2.非静态的可以访问静态的,也可以访问非静态的。
静态变量
1 2 3 4 5 6 7 8 9 10 11 12 13
   | class Employee {     private static int nextId = 1;       private int id;          public Employee() {         id = nextId++;     }          public static int getNextId() {                  return nextId;     } }
  | 
 
静态方法
1 2 3 4 5 6 7 8
   | class MathUtils {     public static double circleArea(double radius) {         return Math.PI * radius * radius;     } }
 
  double area = MathUtils.circleArea(5.0);
  | 
 
静态代码块
1 2 3 4 5 6 7 8 9 10 11 12
   | class Database {     private static Connection conn;          static {                  try {             conn = DriverManager.getConnection("jdbc:mysql://localhost:3306/mydb");         } catch (SQLException e) {             e.printStackTrace();         }     } }
  | 
 
2. final修饰符
final修饰符用于类、方法和变量,具有以下特点:
- 类:被修饰的类不能被继承
 
- 方法:被修饰的方法不能被子类重写
 
- 变量:被修饰的变量(局部变量或类变量)只能赋值一次,不能被更改
 
final变量
1 2 3 4 5 6 7 8 9 10 11 12 13
   | public class Constants {     public static final double PI = 3.141592653589793;     public final int MAX_USERS;            public Constants(int max) {         MAX_USERS = max;       }          void test() {         final int LOCAL_CONST = 100;                } }
  | 
 
final方法
1 2 3 4 5 6 7 8 9
   | class Parent {     public final void importantMethod() {              } }
  class Child extends Parent {      }
  | 
 
final类
1 2 3 4 5 6 7
   | final class StringUtils {       public static boolean isEmpty(String str) {         return str == null || str.trim().isEmpty();     } }
 
 
  | 
 
3. abstract修饰符
抽象类
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
   | abstract class Shape {     protected String color;          public Shape(String color) {         this.color = color;     }               public abstract double area();               public String getColor() {         return color;     } }
  | 
 
抽象方法实现
1 2 3 4 5 6 7 8 9 10 11 12 13
   | class Circle extends Shape {     private double radius;          public Circle(String color, double radius) {         super(color);         this.radius = radius;     }          @Override     public double area() {         return Math.PI * radius * radius;     } }
  | 
 
4. synchronized修饰符
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
   | class Counter {     private int count = 0;               public synchronized void increment() {         count++;     }               public void add(int value) {         synchronized(this) {             count += value;         }     } }
  | 
 
5. volatile修饰符
1 2 3 4 5 6 7 8 9 10 11
   | class SharedObject {     private volatile boolean flag = false;          public void toggleFlag() {         flag = !flag;       }          public boolean isFlag() {         return flag;        } }
  | 
 
6. transient修饰符
1 2 3 4 5 6 7
   | class User implements Serializable {     private String username;     private transient String password;                 private transient CreditCard creditCard; }
  | 
 
7.内部类
在java中,可以将一个类定义在另一个类里面或者一个方法里面,这样的类称为内部类(inner class)或
者嵌套类,广泛意义上的内部类一般分为这四种情况:成员内部类,局部内部类(匿名内部类)和静态
内部类。
成员内部类
蓝图如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
   | class OuterClass {          private int outerVar;               class InnerClass {                  private int innerVar;                           public void innerMethod() {                          System.out.println("OuterVar: " + outerVar);         }     } }
  | 
实际案例:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26
   | package com.iweb.test1;
  public class Car {     private String color;          public String getColor() {         return color;    }     public void setColor(String color) {         this.color = color;    }          public void run(){         System.out.println("汽车开动");    }          public class  Engine{         private float  displacement;                      public void turn(){             System.out.println("引擎正在运行");             System.out.println("汽车颜色:"+color);        }    } }
 
   | 
局部内部类
蓝图如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19
   | class OuterClass {          private int outerVar;               public void outerMethod() {         final int localVar = 100;                    class LocalInnerClass {                          public void innerMethod() {                                  System.out.println("OuterVar: " + outerVar);                                  System.out.println("LocalVar: " + localVar);             }         }     } }
  | 
实际案例:
1 2 3 4 5 6 7 8 9 10 11 12
   |     public class MyOther {          public void method1(){                  class InnerClass{             String name="局部内部类";             public void innerMethod(){                 System.out.println(name);            }        }    } }
  | 
匿名内部类
匿名内部类是一种没有类名的内部类,通常用于创建事件监听器、线程和适配器等。
匿名内部类:匿名类使你的代码更加简洁。如果你只需要使用一个本地类一次,就可以使用他们。
可以如下表达(分块+蓝图)
1 2 3 4 5 6 7
   | MyRun r=new MyRun() {             @Override             public void run() {                 System.out.println("匿名内部类的实现方式");            }        };           r.run();
  | 
或者可以这么写:
1 2 3 4 5 6
   | new MyRun() {             @Override             public void run() {                 System.out.println("匿名内部类的实现方式");            }        }.run();
  | 
这种方式的写法其实就是“匿名部内类”的写法,以前的方式,为了实现接口,不得不去创建一个类实现接口,有了匿名内部类就不必这么麻烦了。
蓝图如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
   | interface MyInterface {     void myMethod(); }
  class MyClass {     public void doSomething() {                  MyInterface myObj = new MyInterface() {             @Override             public void myMethod() {                 System.out.println("Hello from anonymous inner class!");             }         };                           myObj.myMethod();     } }
  | 
javaBean
javaBean就是一个遵循特定设计模式的普通的java类,具备以下特点:
- 属性私有化:把类的属性用 private 修饰,防止外部随便访问或修改,保证数据的安全性和完整性。
 
- 共同的set/get方法:为了让外部能够有限制的访问和修改这些私有属于,会给每一个属性提供一对共
同的set/get方法。 
- 无参构造函数:一般来说,javaBean会提供一个无参的构造函数,这样在创建对象的时候会更加的方便
和灵活。 
满足以上三个条件的标准类设计就是javaBean。
以下是一个标准javaBean的示例:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30
   | public class Student {               private String name;     private int age;                    public Student() {     }               public Student(String name, int age) {         this.name = name;         this.age = age;     }                    public void setName(String name) {         this.name = name;     }               public String getName() {         return name;     }           }
  | 
三、修饰符组合规则
1. 合法组合示例
| 组合 | 
示例 | 
说明 | 
| public static | 
public static void main() | 
主方法必须如此 | 
| public final | 
public final class String | 
不可继承的公共类 | 
| protected abstract | 
protected abstract void draw() | 
需要子类实现的受保护方法 | 
| private static | 
private static Logger log | 
类内部使用的静态工具 | 
| public synchronized | 
public synchronized void put() | 
线程安全的公共方法 | 
 
2. 非法组合及原因
| 非法组合 | 
原因 | 
| abstract final | 
abstract需要继承,final禁止继承 | 
| abstract private | 
private方法不能被子类覆盖 | 
| abstract static | 
static方法不参与多态 | 
| final volatile | 
final不可变,volatile需要可变 | 
| synchronized abstract | 
抽象方法没有实现,无法同步 | 
 
四、类成员修饰符适用表
| 修饰符 | 
类 | 
接口 | 
变量 | 
方法 | 
构造器 | 
代码块 | 
| public | 
✓ | 
✓ | 
✓ | 
✓ | 
✓ | 
× | 
| protected | 
× | 
× | 
✓ | 
✓ | 
✓ | 
× | 
| default | 
✓ | 
✓ | 
✓ | 
✓ | 
✓ | 
× | 
| private | 
× | 
× | 
✓ | 
✓ | 
✓ | 
× | 
| static | 
× | 
× | 
✓ | 
✓ | 
× | 
✓ | 
| final | 
✓ | 
× | 
✓ | 
✓ | 
× | 
× | 
| abstract | 
✓ | 
✓ | 
× | 
✓ | 
× | 
× | 
| synchronized | 
× | 
× | 
× | 
✓ | 
× | 
✓ | 
| volatile | 
× | 
× | 
✓ | 
× | 
× | 
× | 
| transient | 
× | 
× | 
✓ | 
× | 
× | 
× | 
 
五、典型应用场景
1. 单例模式实现
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
   | public class Singleton {     private static volatile Singleton instance;          private Singleton() {}            public static Singleton getInstance() {         if (instance == null) {             synchronized (Singleton.class) {                 if (instance == null) {                     instance = new Singleton();                 }             }         }         return instance;     } }
  | 
 
2. 工具类设计
1 2 3 4 5 6 7 8 9 10 11 12 13
   | public final class StringUtils {          private StringUtils() {}          public static boolean isBlank(String str) {         return str == null || str.trim().isEmpty();     }          public static String reverse(String str) {         if (str == null) return null;         return new StringBuilder(str).reverse().toString();     } }
  | 
 
3. 线程安全计数器
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
   | public class SafeCounter {     private int count;          public synchronized void increment() {         count++;     }          public synchronized int get() {         return count;     }               private AtomicInteger atomicCount = new AtomicInteger(0);          public void atomicIncrement() {         atomicCount.incrementAndGet();     } }
  | 
 
六、修饰符使用最佳实践
- 封装原则:成员变量尽量私有,通过方法控制访问
 
- 最小权限:使用最严格的访问级别(优先private)
 
- static慎用:避免滥用导致内存泄漏和测试困难
 
- final应用:尽可能使变量不可变,减少并发问题
 
- 同步策略:优先使用并发工具类而非synchronized
 
- 抽象设计:抽象类定义框架,具体类实现细节
 
Java运算符全面解析
运算符是Java语言中用于执行各种操作的符号。下面我将系统地讲解Java中的各类运算符及其使用场景。
一、算术运算符
1. 基本算术运算符
| 运算符 | 
名称 | 
示例 | 
说明 | 
| + | 
加法 | 
a + b | 
也可用于字符串连接 | 
| - | 
减法 | 
a - b | 
 | 
| * | 
乘法 | 
a * b | 
 | 
| / | 
除法 | 
a / b | 
整数相除结果取整 | 
| % | 
取模 | 
a % b | 
取余数 | 
 
代码示例:
1 2 3 4 5 6 7 8
   | int a = 10; int b = 3; System.out.println(a + b);   System.out.println(a - b);   System.out.println(a * b);   System.out.println(a / b);   System.out.println(a % b);   System.out.println(10.0 / 3); 
   | 
2. 自增/自减运算符
| 运算符 | 
名称 | 
示例 | 
等价于 | 
| ++i | 
前自增 | 
int j = ++i; | 
i = i + 1; j = i; | 
| i++ | 
后自增 | 
int j = i++; | 
j = i; i = i + 1; | 
| —i | 
前自减 | 
int j = —i; | 
i = i - 1; j = i; | 
| i— | 
后自减 | 
int j = i—; | 
j = i; i = i - 1; | 
 
示例分析:
1 2 3
   | int x = 5; int y = x++;   int z = ++x;  
   | 
二、关系运算符
关系运算符用于比较两个值,返回布尔结果:
| 运算符 | 
名称 | 
示例 | 
说明 | 
| == | 
等于 | 
a == b | 
比较值是否相等 | 
| != | 
不等于 | 
a != b | 
 | 
| > | 
大于 | 
a > b | 
 | 
| < | 
小于 | 
a < b | 
 | 
| >= | 
大于等于 | 
a >= b | 
 | 
| <= | 
小于等于 | 
a <= b | 
 
注意事项:
- 比较引用类型时,
==比较的是引用地址 
- 比较字符串内容应使用
equals()方法 
示例:
1 2 3 4 5 6 7 8 9
   | int a = 10, b = 20; System.out.println(a == b);   System.out.println(a != b);   System.out.println(a > b);   
  String s1 = "hello"; String s2 = new String("hello"); System.out.println(s1 == s2);       System.out.println(s1.equals(s2)); 
   | 
三、逻辑运算符
1. 基本逻辑运算符
| 运算符 | 
名称 | 
示例 | 
说明 | 
| && | 
逻辑与 | 
a && b | 
短路与 | 
| \ | 
\ | 
 | 
逻辑或 | 
a \ | 
\ | 
b | 
短路或 | 
| ! | 
逻辑非 | 
!a | 
取反 | 
 
短路特性示例:
1 2 3 4
   | int x = 5; boolean result = (x < 4) && (x++ < 10); 
  System.out.println(x);  
   | 
2. 位运算符
| 运算符 | 
名称 | 
示例 | 
说明 | 
| & | 
位与 | 
a & b | 
按位与 | 
| \ | 
 | 
位或 | 
a \ | 
b | 
按位或 | 
| ^ | 
位异或 | 
a ^ b | 
相同为0,不同为1 | 
| ~ | 
位非 | 
~a | 
按位取反 | 
| << | 
左移 | 
a << 2 | 
左移,低位补0 | 
| >> | 
右移 | 
a >> 2 | 
右移,高位补符号位 | 
| >>> | 
无符号右移 | 
a >>> 2 | 
右移,高位补0 | 
 
位运算示例:
1 2 3 4 5 6 7 8
   | int a = 60;     int b = 13;     System.out.println(a & b);    System.out.println(a | b);    System.out.println(a ^ b);    System.out.println(~a);       System.out.println(a << 2);   System.out.println(a >> 2);  
   | 
四、赋值运算符
1. 基本赋值运算符
| 运算符 | 
示例 | 
等价于 | 
| = | 
a = b | 
 | 
| += | 
a += b | 
a = a + b | 
| -= | 
a -= b | 
a = a - b | 
| *= | 
a *= b | 
a = a * b | 
| /= | 
a /= b | 
a = a / b | 
| %= | 
a %= b | 
a = a % b | 
 
复合赋值示例:
1 2 3 4
   | int x = 10; x += 5;    x *= 2;    x %= 7;   
   | 
2. 位运算赋值运算符
| 运算符 | 
示例 | 
等价于 | 
| &= | 
a &= b | 
a = a & b | 
| \ | 
= | 
a \ | 
= b | 
a = a \ | 
b | 
| ^= | 
a ^= b | 
a = a ^ b | 
| <<= | 
a <<= b | 
a = a << b | 
| >>= | 
a >>= b | 
a = a >> b | 
| >>>= | 
a >>>= b | 
a = a >>> b | 
 
五、条件运算符(三元运算符)
语法:条件 ? 表达式1 : 表达式2
示例:
1 2 3 4
   | int a = 10, b = 20; int max = (a > b) ? a : b;  
  String result = (score >= 60) ? "及格" : "不及格";
   | 
六、instanceof运算符
用于检查对象是否是特定类的实例:
1 2 3 4 5 6 7 8
   | Object obj = "hello"; System.out.println(obj instanceof String);   System.out.println(obj instanceof Integer); 
  class Vehicle {} class Car extends Vehicle {} Car car = new Car(); System.out.println(car instanceof Vehicle); 
   | 
 
七、运算符优先级
下表按优先级从高到低排列:
| 优先级 | 
运算符 | 
结合性 | 
| 1 | 
() [] . | 
左→右 | 
| 2 | 
! ~ ++ — +(正) -(负) | 
右→左 | 
| 3 | 
* / % | 
左→右 | 
| 4 | 
+ - | 
左→右 | 
| 5 | 
<< >> >>> | 
左→右 | 
| 6 | 
< <= > >= instanceof | 
左→右 | 
| 7 | 
== != | 
左→右 | 
| 8 | 
& | 
左→右 | 
| 9 | 
^ | 
左→右 | 
| 10 | 
\ | 
 | 
左→右 | 
| 11 | 
&& | 
左→右 | 
| 12 | 
\ | 
\ | 
 | 
左→右 | 
| 13 | 
?: | 
右→左 | 
| 14 | 
= += -= *= /= %= &= \ | 
= ^= <<= >>= >>>= | 
右→左 | 
 
优先级示例:
1 2
   | int result = 5 + 3 * 2;       boolean flag = 5 > 3 && 2 < 4; 
   | 
八、特殊运算符技巧
1. 交换变量值
1 2 3 4 5
   | int a = 5, b = 10; a = a ^ b; b = a ^ b; a = a ^ b;
 
   | 
 
2. 判断奇偶
1 2 3 4 5
   | if ((num & 1) == 0) {     System.out.println("偶数"); } else {     System.out.println("奇数"); }
  | 
 
3. 快速乘除2的幂次
1 2 3
   | int n = 8; n = n << 1;   n = n >> 2;  
   | 
 
九、常见问题与陷阱
整数除法:
1 2
   | double d = 5 / 2;   double d2 = 5.0 / 2; 
   | 
 
 
浮点数比较:
1 2 3 4 5
   |  if (f1 == f2) {...}
 
  if (Math.abs(f1 - f2) < 1e-6) {...}
 
  | 
 
 
字符串比较:
1 2 3 4
   | String s1 = "hello"; String s2 = new String("hello"); System.out.println(s1 == s2);       System.out.println(s1.equals(s2)); 
   | 
 
 
运算符优先级混淆:
1 2
   | int x = 5 + 3 * 2;     boolean b = 5 > 3 == true; 
   |