越狱模拟器:挖掘免安装绿色中文版
6.2G · 2025-10-31
作为一名Java后端开发者,Spring的依赖注入是我们每天都要打交道的功能。记得刚学Spring时,我就像走进了一家琳琅满目的糖果店:
@Autowired:Spring家的招牌糖果@Resource:JSR-250标准糖果final + @RequiredArgsConstructor神秘组合这么多选择,我该pick谁?今天,就让我们一起来解开这个甜蜜的烦恼!
@Service
public class UserService {
    @Autowired // 简单粗暴,直接上场
    private UserRepository userRepo;
    
    // 或者通过setter方法
    @Autowired
    public void setUserRepo(UserRepository userRepo) {
        this.userRepo = userRepo;
    }
}
@Autowired是Spring框架的亲儿子,默认按类型(byType)进行装配。当有多个相同类型的bean时,就需要@Qualifier注解来指定具体装配哪个bean。
@Service
public class UserService {
    @Resource(name = "userRepository") // 按名称来装配
    private UserRepository userRepo;
}
@Resource是Java自带的注解(JSR-250),默认按名称(byName)进行装配。如果找不到名称匹配的bean,才会退回到按类型装配。
这两种方式虽然简单,但存在几个问题:
在我们介绍新王者之前,先要了解什么是构造器注入:
@Service
public class UserService {
    private final UserRepository userRepo;
    private final EmailService emailService;
    
    // 手动编写构造器
    public UserService(UserRepository userRepo, EmailService emailService) {
        this.userRepo = userRepo;
        this.emailService = emailService;
    }
}
Spring会智能地找到这个构造器,并自动传入所需的依赖。但手动写构造器很麻烦,尤其是依赖很多的时候...
这时候,Lombok的@RequiredArgsConstructor就派上用场了:
@Service
@RequiredArgsConstructor // 一个注解代替所有!
public class UserService {
    private final UserRepository userRepo;
    private final EmailService emailService;
    // 不需要手动写构造器了!
}
编译后,Lombok会自动生成这样的代码:
@Service
public class UserService {
    private final UserRepository userRepo;
    private final EmailService emailService;
    
    // Lombok自动生成的构造器
    public UserService(UserRepository userRepo, EmailService emailService) {
        this.userRepo = userRepo;
        this.emailService = emailService;
    }
}
final关键字保证了依赖一旦注入就无法更改,线程安全杠杠的!让我们通过一个表格来直观对比三位选手:
| 特性 | @Autowired | @Resource | final + @RequiredArgsConstructor | 
|---|---|---|---|
| 来源 | Spring框架 | Java标准 | Spring + Lombok组合技 | 
| 注入方式 | 按类型 | 按名称 | 按类型(构造器) | 
| 不可变性 | ❌ | ❌ | ✅ | 
| 代码简洁度 | 中等 | 中等 | 极高 | 
| 测试友好度 | 较差 | 较差 | 极好 | 
| 循环依赖检测 | 运行时 | 运行时 | 启动时 | 
| 推荐程度 | 不推荐 | 不推荐 | 强烈推荐 | 
让我们来看一个完整的使用示例:
@Service
@RequiredArgsConstructor
@Slf4j // 这也是Lombok的好用功能,自动提供log对象
public class OrderService {
    private final OrderRepository orderRepo;
    private final PaymentService paymentService;
    private final NotificationService notificationService;
    
    public Order createOrder(Order order) {
        Order savedOrder = orderRepo.save(order);
        paymentService.processPayment(savedOrder);
        notificationService.sendOrderConfirmation(savedOrder);
        log.info("Order created successfully: {}", savedOrder.getId());
        return savedOrder;
    }
}
// 测试代码也变得异常简单
public class OrderServiceTest {
    @Test
    public void testCreateOrder() {
        // 直接通过构造器传入mock对象
        OrderRepository mockRepo = mock(OrderRepository.class);
        PaymentService mockPayment = mock(PaymentService.class);
        NotificationService mockNotification = mock(NotificationService.class);
        
        OrderService orderService = new OrderService(mockRepo, mockPayment, mockNotification);
        
        // 进行测试...
    }
}
@Autowired标注Spring应该使用哪个@NonNull注解:@RequiredArgsConstructor
public class ExampleService {
    private final @NonNull Optional<AdditionalService> additionalService;
}
朋友们,时代在变,编程的最佳实践也在不断演进。从最早的XML配置,到注解注入,再到现在的构造器注入,我们一直在追求更优雅、更安全的代码编写方式。
final + @RequiredArgsConstructor不仅仅是一种技术选择,更是一种编程哲学的体现:明确依赖、不可变状态、易于测试。这些都是编写健壮、可维护代码的关键要素。
所以,下次当你需要注入依赖时,不妨试试这个组合拳,让你的代码变得更加坚固而优雅!
互动时间:大家在项目中更喜欢用哪种注入方式呢?欢迎在评论区分享你的经验和看法!
 
                    