Ja 企业应用基础及开发- 4_第1页
Ja 企业应用基础及开发- 4_第2页
Ja 企业应用基础及开发- 4_第3页
Ja 企业应用基础及开发- 4_第4页
Ja 企业应用基础及开发- 4_第5页
已阅读5页,还剩38页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

5.1依赖注入5.1依赖注入详解01知识目标理解依赖注入的核心作用(解耦组件依赖关系)掌握3种注入实现方式(构造器/Setter/字段注入)区分各注入方式的适用场景与局限性02能力目标编写符合阿里巴巴开发规范的注入代码诊断并解决常见注入失败问题设计可维护的依赖注入结构03本节定位前置知识:4.2SpringIoC容器基础后续内容:5.2注解实现IoC高级配置学习目标与知识地图传统开发困境publicclassOrderService{//硬编码依赖导致紧耦合privateUserDaouserDao=newUserDaoImpl();privateLogServicelogService=newLogServi}-修改实现类需重构代码,违背开闭原则!依赖注入解决方案控制反转:对象创建权移交IoC容器依赖注入:容器通过预设方式自动注入依赖对象解耦效果:组件间通过接口交互,实现“面向接口编程”生活类比如同点餐时只需告知需求(声明依赖),厨师(容器)负责食材准备(对象创建)和送餐(注入),食客无需关心烹饪过程!依赖注入概念与价值三种注入方式核心对比注入方式实现方式优点缺点适用场景构造器注入类构造方法参数强制依赖(不可变)支持final字段便于单元测试多个依赖时参数冗长核心服务(如支付服务)Setter注入setXxx()方法可选依赖支持支持重新注入无法注入final字段依赖状态可变非核心可选组件字段注入@Autowired直接标注字段代码简洁开发效率高隐藏依赖关系无法注入final字段简单Demo或原型开发Spring官方建议:构造器注入为首要选择,Setter注入用于可选依赖,字段注入谨慎使用!IoC容器注入流程图依赖注入核心流程01定位阶段(Locate):扫描@ComponentScan指定路径,识别@Service标注的Bean类。02加载阶段(Load):将Bean定义解析为BeanDefinition,存储到BeanDefinitionRegistry。03注入阶段(Inject):创建目标Bean实例,根据注入方式(构造器/Setter)注入依赖,完成初始化并放入容器。关键类DefaultListableBeanFactory

负责注入逻辑,AutowiredAnnotationBeanPostProcessor

处理@Autowired注解解析。01完整代码文件结构com.example├─service│├─UserService.java//用戶服务类(含构造器注入)│└─LogService.java//日志服务类(被依赖组件)├─config│└─AppConfig.java//IoC容器配置类└─Main.java//应用启动类02依赖说明UserService依赖LogService(通过构造器注入)所有类位于com.example包下,符合Spring组件扫描规范需引入SpringContext6.1.0依赖(Maven/Gradle配置略)实例项目结构树构造器注入代码实现LogService.java完整代码packagecom.example.service;importorg.springframework.stereotype.Service;@Service

//标记为Spring管理的BeanpublicclassLogService{

publicvoidlog(Stringmessage){System.out.println("[系统⽇志]"+message);}}UserService.java构造器注入实现packagecom.example.service;importorg.springframework.stereotype.Service;@ServicepublicclassUserService{

privatefinalLogServicelogService;//final字段确保不可变

//构造器注⼊(Spring6.x可省略@Autowired)

publicUserService(LogServicelogService){

this.logService=logService;System.out.println("UserService构造器执⾏,注⼊LogService}

publicvoidcreateUser(Stringusername){logService.log("⽤⼾创建:"+username);//使⽤注⼊的依赖Setter注入与字段注入代码实现UserService.javaSetter注入改造packagecom.example.service;importorg.springframework.beans.factory.annotation.Autowired;importorg.springframework.stereotype.Service;@ServicepublicclassUserService{privateLogServicelogService;//⾮final字段@Autowired(required=false)//可选依赖publicvoidsetLogService(LogServicelogService){this.logService=logService;System.out.println("Setter注⼊执⾏");}publicvoidcreateUser(Stringusername){if(logService!=null){logService.log("⽤⼾创建:"+username);}else{System.out.println("未注⼊⽇志服务...");}UserService.java字段注入实现packagecom.example.service;importorg.springframework.beans.factory.annotation.importorg.springframework.stereotype.Service;@ServicepublicclassUserService{@AutowiredprivateLogServicelogService;publicvoidcreateUser(Stringusername){logService.log("⽤⼾创建:"+username);}}使用警告:无法注入final字段单元测试需通过Spring容器隐藏依赖关系阿里巴巴开发手册:禁止在业务代码中使用字段注入!配置类与运行主类代码实现AppConfig.java配置类packagecom.example.config;importorg.springframework.context.annotation.ComponentScan;importorg.springframework.context.annotation.Configuration;@Configuration

//标记为Spring配置类@ComponentScan(basePackages="com.example.service")//扫描service包下的所有@Component注解类public

class

AppConfig{

//⽆需额外配置,IoC容器会⾃动发现并管理Bean}Main.java启动类packagecom.example;importcom.example.config.AppConfig;importcom.example.service.UserService;importorg.springframework.context.annotation.Annotatipublic

class

Main{

public

static

void

main(String[]args){

//1.初始化IoC容器(基于注解配置)

try(AnnotationConfigApplicationContextcontex

new

AnnotationConfigApplicationContext

System.out.println("IoC容器初始化完成,Bean数

//2.从容器获取UserServiceBean

UserServiceuserService=context.getBean(

//3.调⽤业务⽅法userService.createUser("张三");}

//4.try-with-resources⾃动关闭容器关键API:AnnotationConfigApplicationContext是注解配置的IoC容器实现类运行结果、最佳实践与总结运行结果IoC容器初始化完成,Bean数量:2UserService构造器执⾏,注⼊LogService[系统⽇志]⽤⼾创建:张三常见异常排查NoSuchBeanDefinitionException:检查@ComponentScan路径或@Service注解NullPointerException:确保依赖已正确注入(构造器注入可避免此问题)企业级最佳实践核心服务→构造器注入;多依赖→@RequiredArgsConstructor简化;依赖冲突→@Qualifier指定Bean名称总结依赖注入是IoC容器核心实现,构造器注入为官方推荐企业开发需遵循最佳实践,避免字段注入在业务代码中使用下节预告:5.2注解实现IoC高级配置课后练习:用三种注入方式实现用户管理模块并对比开发效率与可维护性5.2注解实现IoC欢迎进入Spring注解开发实战模块,本节将聚焦如何通过注解简化IoC容器配置,摆脱XML配置的繁琐,学习核心注解的使用方法、组件扫描机制及最佳实践。学习目标与知识图谱知识目标掌握IoC核心注解分类及使用场景、理解@ComponentScan扫描机制、区分@Bean与@Component适用场景、对比@Autowired与@Resource差异。能力目标独立使用纯注解配置IoC容器、管理Bean生命周期、诊断解决常见异常。本节定位前置基础为5.1依赖注入,核心内容是注解驱动IoC配置,后续延伸至5.3注解实现AOP。注解配置vsXML配置传统XML配置痛点:文件冗长、维护成本高、易出错、开发效率低。注解配置优势:开发效率高(自动扫描)、可读性强(代码与配置结合)、维护成本低(支持部分热部署)。维度XML配置注解配置开发效率低(手动编写)高(自动扫描)可读性低(配置与代码分离)高(配置与代码结合)维护成本高(修改需重启)低(支持部分热部署)适用场景复杂基础设施(数据源)日常Bean定义与依赖注入Spring官方趋势:纯注解配置已成主流,SpringBoot自动配置进一步简化IoC容器配置。核心IoC注解分类表组件注解@Component(通用组件)、@Service(服务层)、@Repository(DAO层)、@Controller(Web层),应用于类级别,被@ComponentScan扫描注册。配置注解@Configuration(标记配置类)、@ComponentScan(指定扫描路径)、@Bean(自定义Bean创建方法)。依赖注解@Autowired(Spring提供,按类型注入)、@Qualifier(配合@Autowired指定名称)、@Resource(JDK内置,按名称后按类型注入)。@ComponentScan扫描机制路径定位默认扫描@Configuration类所在包,可通过basePackages自定义路径,如@ComponentScan(basePackages={"com.example.service","com.example.dao"})。过滤规则通过includeFilters/excludeFilters自定义,支持ANNOTATION(按注解)、ASSIGNABLE_TYPE(按类/接口)、REGEX(按正则)等FilterType。Bean注册扫描到的组件自动注册为Bean,默认名称为首字母小写类名,可通过@Component("customName")指定。01项目结构概览项目结构包含config

包(配置类AppConfig)、service包(业务服务类UserService、OrderService等)、以及Main

启动类。02核心包职责config

包存放核心配置类,定义组件扫描和Bean;service

包存放@Service标记的业务组件,实现依赖注入;Main

类初始化IoC容器并验证配置。03架构优势此结构遵循分层架构,通过注解驱动开发,消除了传统的XML配置文件,使得项目整体更加简洁、高效,易于维护和扩展。实例项目结构@Configuration配置类@Configuration注解标记配置类,替代XML配置文件,相当于<beans>标签。@ComponentScan指定扫描路径,basePackages属性接收包路径数组,默认扫描配置类所在包及其子包。示例代码@Configuration@ComponentScan(basePackages="com.example.service")public

class

AppConfig

{}配置类优势:类型安全、支持复杂逻辑、IDE自动补全与编译时检查。常见问题:扫描路径错误导致Bean无法注册,抛出NoSuchBeanDefinitionException。@Service组件类@Service

注解用于标记服务层(ServiceLayer)组件,使代码的语义化更强,便于Spring框架进行AOP切面定向,实现事务管理、日志记录等横切关注点。UserService示例:@ServicepublicclassUserService{privatefinalOrderServiceorderService;

//构造器注入(Spring6.x可省略@Autowired)publicUserService(OrderServiceorderService){this.orderService=orderService;}}OrderService示例:@Service("orderService")publicclassOrderService{publicintgetOrderCount(LonguserId){

//...业务逻辑...}}构造器注入优势:确保依赖在对象创建时就被正确初始化,避免了使用`null`的风险;通过`final`关键字保证依赖不可变;同时,这种方式也更便@Bean自定义Bean@Bean注解用于在配置类中自定义Bean的创建方法,特别适用于实例化第三方组件或需要进行复杂初始化逻辑的对象。示例代码@Bean(initMethod="init",destroyMethod="destroy")public

DateService

dateService(){DateServicedateService=newDateService();dateService.setFormat("yyyy-MM-ddHH:mm:ss");returndateService;}@Bean(name={"sysTime","systemTime"})publicDatesystemTime(){returnnewDate();}

Bean生命周期管理通过`initMethod`指定的方法会在Bean初始化完成后被调用;通过`destroyMethod`指定的方法会在Spring容器关闭时被调用(此特性仅对单例Bean有效)。启动类与容器初始化Main类使用AnnotationConfigApplicationContext加载配置类,从而完成IoC容器的初始化工作。代码示例try(AnnotationConfigApplicationContextcontext=newAnnotationConfigApplicationContext(AppConfig.class)){System.out.println("Bean总数:"

+context.getBeanDefinitionCount());UserServiceuserService=context.getBean(UserService.class);}预期Bean:AppConfig、UserService、OrderService、dateService、systemTime(共5个)。try-with-resources确保容器在使用后自动关闭,从而触发Bean的销毁方法。组件扫描高级配置@ComponentScan高级属性:basePackages指定扫描根路径,includeFilters/excludeFilters自定义规则,useDefaultFilters禁用默认规则。FilterType类型:ANNOTATION(按注解)、ASSIGNABLE_TYPE(按类/接口)、REGEX(按正则)、ASPECTJ(按AspectJ表达式)、CUSTOM(自定义TypeFilter)。示例代码@ComponentScan(basePackages="com.example",includeFilters={@Filter(type=ANNOTATION,classes=Service.class),@Filter(type=ASSIGNABLE_TYPE,classes=UserDao.class)},excludeFilters=@Filter(type=REGEX,pattern=".*Test.*"),useDefaultFilters=false)@Autowired与@Resource对比特性@Autowired@Resource来源Spring特有JDK内置(JSR-250)默认注入方式按类型(byType)按名称(byName)后按类型注解位置支持字段、构造器、方法字段、方法(不支持构造器)依赖required特性有(默认true)无最佳实践纯Spring项目用@Autowired+@Qualifier,跨框架项目用@Resource,构造器注入优先。运行结果与解析预期控制台输出DateService初始化,格式:yyyy-MM-ddHH:mm:ss容器初始化完成,Bean总数:5User_1001,OrderCount:42系统时间:MonOct0220:51:38CST2025DateService销毁结果解析验证组件扫描、@Bean注册、依赖注入、生命周期管理均正常工作。异常排查启示Bean总数不符检查扫描路径,NPE检查依赖注入,初始化失败检查@Bean方法。常见问题与解决方案NoSuchBeanDefinitionException:组件未标注注解、扫描路径错误、@Bean定义错误→检查注解、验证扫描路径、修正@Bean方法。NoUniqueBeanDefinitionException:同类型多Bean未指定→@Qualifier或@Resource(name)。NullPointerException:依赖注入失败→确保依赖存在、使用构造器注入、处理null情况。BeanCreationException:@Bean方法异常→检查初始化逻辑、添加异常处理。构造器循环依赖:A依赖B且B依赖A→@Lazy或Setter注入。总结与企业级实践核心知识点总结注解实现IoC核心是@ComponentScan

自动扫描组件,注解体系分组件、配置、依赖三类,@Bean

与@Component

适用场景不同,@Autowired

与@Resource

各有优劣。企业级实践配置类命名XXXConfig,@Bean

方法名与类型一致,多层级配置拆分与@Import

整合,第三方组件集中配置,优先构造器注入。下节预告5.3注解实现AOP。5.3注解实现AOP学习目标与知识图谱知识目标·理解AOP的核心思想与解决的痛点问题·掌握AOP核心术语(切面、通知、切点等)·熟练使用@AspectJ注解体系(@Aspect、@Pointcut等)·掌握切点表达式语法(execution、within等)·区分五种通知类型的执行时机与应用场景能力目标·使用纯注解方式开发完整AOP切面·编写复杂切点表达式匹配目标方法·实现环绕通知进行方法增强与性能监控·解决AOP切面优先级与参数传递问题本节定位前置基础:5.2注解实现IoC(提供AOP的容器支持)核心内容:@AspectJ注解驱动AOP开发全流程后续应用:事务管理(@Transactional)、安全控制等企业级特性AOP概念与传统开发痛点传统开发中的横切逻辑问题在分层架构中,日志记录、权限检查、事务控制等横切逻辑分散在各业务方法中,导致:代码耦合度高,横切逻辑与业务逻辑交织代码复用率低,相同逻辑重复编写维护成本高,修改需改动多个业务类违反单一职责原则@ServicepublicclassUserService{publicvoidcreateUser(Useruser){//横切逻辑:日志("创建用戶:"+user.getName());//横切逻辑:权限检查if(!hasPermission()){thrownewAccessDeniedException();}//业务逻辑userDao.insert(user);//横切逻辑:事务提交transactionMmit();}}AOP解决方案与核心价值AOP通过“横切”技术将横切逻辑抽取为切面,动态织入目标方法,实现:业务逻辑与横切逻辑分离,代码结构清晰横切逻辑复用性提高,一次定义多处使用降低维护成本,修改横切逻辑无需改动业务代码符合开闭原则,扩展功能不修改原有代码生活类比:AOP如同电影院的“字幕系统”,字幕(横切逻辑)独立于电影内容(业务逻辑),动态叠加且不影响电影本身。AOP核心术语表AOP核心术语定义与关系术语定义通俗理解切面(Aspect)封装横切逻辑的类,包含切点和通知如“日志切面”“事务切面”通知(Advice)切面中的具体横切逻辑方法(前置、后置等)如“日志记录方法”切点(Pointcut)定义哪些类的哪些方法需要被织入通知“匹配所有service包下的save*方法”连接点(JoinPoint)程序执行过程中可被AOP织入的点(如方法调用)“UserService.createUser()方法执行时”织入(Weaving)将切面应用到目标对象并创建代理对象的过程“将日志切面织入UserService”目标对象(Target)被AOP织入横切逻辑的原始对象“UserService的实例”代理对象(Proxy)织入切面后生成的对象,包含原始业务逻辑和横切逻辑“UserService的代理对象”关键关系:切面=切点+通知,即“在哪些方法(切点)执行什么横切逻辑(通知)”。@AspectJ注解体系表@AspectJ核心注解功能说明注解作用域功能描述@Aspect类标记当前类为切面类,需配合@Component注解被Spring容器扫描@Pointcut方法定义切点表达式,该方法名可作为其他通知的切点引用(方法体通常为空)@Before方法前置通知:在目标方法执行前执行@AfterReturning方法返回后通知:在目标方法正常返回后执行(异常时不执行)@AfterThrowing方法异常通知:在目标方法抛出异常后执行@After方法最终通知:在目标方法执行后执行(无论正常返回还是异常,类似finally)@Around方法环绕通知:包裹目标方法,可在执行前后自定义逻辑,拥有最大控制权@Order类/方法指定切面优先级,值越小优先级越高(解决多个切面执行顺序问题)使用要求:切面类需同时标注@Aspect和@Component(或通过@Bean注册)配置类需添加@EnableAspectJAutoProxy注解开启AOP支持方法常返仅作为点标识切点表达式语法详解execution表达式核心语法execution([修饰符]返回值类型

包名.类名.方法名(参数类型)[异常类型])通配符说明:·*:匹配任意字符(不匹配.),如*Service匹配所有以Service结尾的类。·..:匹配任意字符,用于包名(匹配子包)和参数(匹配任意参数)。·+:匹配指定类及其子类,如UserService+匹配UserService及其实现类。实战示例与其他指示器execution示例:1.匹配com.example.service包下所有类的public方法:execution(public

*com.example.service.*.*(..))2.匹配UserService中返回值为String、参数为Long的方法:execution(Stringcom.example.service.UserService.*(Long))3.匹配所有service包及其子包的方法:execution(*com.example.service...*(..))其他切点指示器:·within:按类匹配,如within(com.example.service.*)·@annotation:按方法注解匹配,如@annotation(Transactional)·args:按参数类型匹配,如args(Long,String)最佳实践:优先使用execution表达式,复杂场景可组合使用(如通知类型对比表通知类型注解执行时机能否修改返回值能否处理异常典型应用场景前置通知@Before目标方法执行前否否权限检查、参数校验返回后通知@AfterReturning目标方法正常返回后可修改返回值否日志记录、数据统计异常通知@AfterThrowing目标方法抛出异常后否可处理异常异常监控、错误报警最终通知@After目标方法执行后(无论是否异常)否否资源释放、清理操作环绕通知@Around包裹目标方法(前+后)可修改返回值可处理异常性能监控、事务控制环绕通知示例@Around("execution(*com.example.service.*.*(..))")publicObjectaround(ProceedingJoinPointjoinPoint)throwsThrowable{longstart=System.currentTimeMillis();try{Objectresult=joinPceed();//执⾏⽬标⽅法returnresult;实例项目结构项目包结构com.example├─aspect//切面类包│└─LogAspect.java//日志切面(@Aspect)├─config//配置类包│└─AppConfig.java//主配置类(@EnableAspectJAutoProxy)├─service//业务服务包│├─UserService.java//用戶服务(目标对象)│└─OrderService.java//订单服务(目标对象)└─Main.java//启动类依赖说明:需引入spring-context和spring-aspects依赖LogAspect:标注@Aspect和@Component,定义切点和通知AppConfig:标注@Configuration和@EnableAspectJAutoProxyAOP执行流程1.启动容器→扫描@Component→发现@Aspectbean(LogAspect)2.@EnableAspectJAutoProxy→开启AOP代理3.容器为目标对象→(UserService等)创建代理对象4.调用目标方法时→代理对象拦截调用→执行切面通知→执行目标方法5.目标方法执行完毕→返回结果(通知可增强结果)切面类完整代码LogAspect.java核心代码packagecom.example.aspect;importorg.aspectj.lang.JoinPoint;importorg.aspectj.lang.ProceedingJoinPoint;importorg.aspectj.lang.annotation.*;importorg.springframework.stereotype.Component;@Aspect//标记为切面类@Component//注册为SpringBeanpublicclassLogAspect{//定义切点:匹配service包下所有类的所有方法@Pointcut("execution(*com.example.service.*.*(..))")publicvoidservicePointcut(){}//切点标识方法(方法体为空)//前置通知@Before("servicePointcut()")publicvoidbefore(JoinPointjoinPoint){Stringmethod=joinPoint.getSignature().getName();Object[]args=joinPointgetArgs();关键注解解析@Aspect:声明此类为切面类,Spring会识别并处理其中的通知。@Pointcut:定义切点表达式,`servicePointcut()`作为后续通知的切点引用。@Before:引用`servicePointcut()`切点,在目标方法执行前触发。@Around:通过`ProceedingJoinPoint`控制目标方法执行,计算执行时间。JoinPoint:提供目标方法信息(如方法名、参数),`ProceedingJoinPoint`为其子接口支持执行目标方法切点定义与复用技巧切点复用与组合@Aspect@ComponentpublicclassLogAspect{//基础切点:所有服务类@Pointcut("within(com.example.service.*)")publicvoidserviceLayer(){}//扩展切点:所有以save开头的⽅法@Pointcut("execution(*save*(..))")publicvoidsaveMethods(){}//组合切点:服务层的save⽅法@Pointcut("serviceLayer()&&saveMethods()")publicvoidserviceSaveMethods(){}//使⽤组合切点@Before("serviceSaveMethods()")publicvoidbeforeSave(JoinPointjoinPoint){System.out.println("保存操作:"+joinPoint.getSignature().getName());}@annotation切点与优先级自定义注解切点示例1.定义@Log注解:@Target(ElementType.METHOD)@Retention(RetentionPolicy.RUNTIME)public@interfaceLog{}2.切点匹配标注@Log的方法:@Pointcut("@annotation(com.example.annotatipublicvoidlogAnnotatedMethods(){}3.在目标方法使用@Log:@ServicepublicclassUserService{@LogpublicvoidcreateUser(){}}切面优先级通过@Order指定(值越小优先级越高)@Aspect@Component@Order(1)//优先级⾼于Order(2)的切⾯五种通知类型代码实现LogAspect中五种通知完整实现@Aspect@Componentpublic

class

LogAspect

{@Pointcut("execution(*com.example.service.*.*(..))")publicvoidpointcut(){}

//1.前置通知@Before("pointcut()")publicvoidbefore(JoinPointjoinPoint){Stringmethod=joinPoint.getSignature().getName();System.out.println("[Before]"+method+"执行前");}

//2.返回后通知@AfterReturning(value="pointcut()",returning="result")publicvoidafterReturning(JoinPointjoinPoint,Objectresult){System.out.println("[AfterReturning]返回值:"+result);通知执行顺序正常执行流程:@Around前→@Before→目标方法→@Around后→@After→@AfterReturning异常执行流程:@Around前→@Before→目标方法(抛出异常)→@After→@AfterThrowing注意:环绕通知必须调用ceed(),否则目标方法不会执行。异常通知仅在目标方法抛出异常时执行,返回后通知不执行。AOP配置类与代理类型AppConfig配置类代码packagecom.example.config;importorg.springframework.context.annotation.ComponentScan;importorg.springframework.context.annotation.Configuration;importorg.springframework.context.annotation.EnableAspectJAutoProxy;@Configuration@ComponentScan(basePackages="com.example")//扫描组件(切⾯和服务)@EnableAspectJAutoProxy(proxyTargetClass=false)//开启AOP代理,proxyTargetClass=false使⽤JDK动态代理,true使⽤CGLIBpublicclassAppConfig{//无需额外配置,@EnableAspectJAutoProxy是核⼼}@EnableAspectJAutoProxy属性proxyTargetClass:是否强制使用CGLIB代理(默认false)false:目标类实现接口时用JDK代理,否则用CGLIBtrue:所有代理都用CGLIB(可代理无接口的类)exposeProxy:是否暴露代理对象到ThreadLocal(默认false),解决自调用不增强问题JDK代理vsCGLIB代理对比特性JDK动态代理CGLIB代理原理实现目标接口继承目标类(生成子类)要求目标类必须实现接口目标类不能是final性能接口方法调用快方法调用稍慢(但创建代理快)代理对象类型接口实现类目标类的子类自调用问题目标对象内部方法调用不会触发AOP增强,需通过AopContext.currentProxy()获取代理对象调用。目标服务类代码示例UserService.javapackagecom.example.service;importorg.springframework.stereotype.Service;@ServicepublicclassUserService{p

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论