从概念和设计哲学的角度详细解析工厂模式
从概念和设计哲学的角度详细解析工厂模式。
1. 工厂模式的核心目标
解耦:将对象的创建过程与使用过程分离,使用者无需关心对象如何被创建。
统一入口:通过一个接口或方法控制对象的生成,隐藏底层实现细节。
类比现实中的工厂:
想象你需要一把椅子,不需要知道木材如何切割、螺丝如何安装,只需告诉工厂“我要一把椅子”,工厂会根据需求生产符合标准的椅子。
2. 三种工厂模式的区别
① 简单工厂模式(Simple Factory)
- 核心思想:
一个“全能工厂”根据输入参数决定创建哪种具体对象。
例如:输入“圆形”,工厂生产圆形按钮;输入“方形”,生产方形按钮。 - 适用场景:
对象类型较少,创建逻辑简单,且不需要频繁扩展新类型。 - 缺点:
不符合“开闭原则”(对扩展开放,对修改关闭)。新增类型时需要修改工厂类的逻辑。
② 工厂方法模式(Factory Method)
- 核心思想:
每个产品由对应的“专属工厂”创建。父类定义抽象工厂方法,子类实现具体对象的创建。
例如:
-
汽车工厂
是抽象父类,定义create_car()
方法。特斯拉工厂
子类生产电动车,丰田工厂
子类生产燃油车。
- 适用场景:
需要灵活扩展新类型,且希望不同工厂独立控制创建逻辑。 - 优势:
符合开闭原则。新增产品时只需新增子类工厂,无需修改已有代码。
③ 抽象工厂模式(Abstract Factory)
- 核心思想:
创建多个相关联的产品族(一组有逻辑联系的产品)。
例如:
-
- 操作系统UI组件:
Windows风格工厂生产Windows按钮、Windows输入框;
Mac风格工厂生产Mac按钮、Mac输入框。 - 家具工厂:
现代风格工厂生产现代沙发+现代茶几;
古典风格工厂生产古典沙发+古典茶几。
- 操作系统UI组件:
- 适用场景:
需要确保一组产品之间的兼容性(例如同一风格的UI组件)。 - 关键区别:
工厂方法模式关注单一产品的创建,抽象工厂模式关注多个相关产品的组合。
3. 工厂模式的优势
- 降低耦合度:
使用者无需依赖具体类,只需依赖抽象接口(如Pizza
接口而非CheesePizza
类)。 - 提升可维护性:
对象创建逻辑集中管理,修改时只需调整工厂类。 - 增强扩展性:
新增产品类型时,对现有代码影响最小(尤其是工厂方法/抽象工厂模式)。
4. 如何选择工厂模式?
场景 | 推荐模式 | 原因 |
对象类型少,且不频繁变化 | 简单工厂 | 快速实现,逻辑简单 |
需要灵活扩展新类型 | 工厂方法 | 通过子类化实现扩展,符合开闭原则 |
需要创建一组关联对象 | 抽象工厂 | 保证产品族的兼容性 |
5. 工厂模式的本质
- 封装变化:
将“对象创建”这种易变的部分封装起来,避免变化扩散到系统其他部分。
例如:若从MySQL
数据库切换到PostgreSQL
,只需更换数据库工厂,其他代码无需修改。 - 面向接口编程:
依赖抽象(如Pizza
接口),而非具体实现(如CheesePizza
类),提高系统灵活性。
6. 工厂模式与其他模式的关系
- 与建造者模式(Builder):
工厂模式关注生产对象,建造者模式关注分步骤构建复杂对象。
例如:工厂直接返回一个完整的汽车对象,建造者模式则分步骤组装发动机、轮胎等。 - 与依赖注入(DI):
依赖注入容器(如Spring框架)本质是工厂模式的升级版,自动化管理对象的创建和生命周期。
总结
工厂模式是面向对象设计中“分工协作”思想的体现:
- 简单工厂:集中化生产,适合简单场景。
- 工厂方法:分权到子类,适合扩展新类型。
- 抽象工厂:生产配套产品,适合关联对象组。
其核心是通过“抽象”隔离变化,让系统更健壮、更易维护。
工厂模式 酒店订单导入系统的设计,我将从架构设计、代码实现和优化建议三个维度进行系统化解析:
一、架构设计解析
1. 分层架构
系统采用典型的分层架构设计:
[表示层] → [应用层] → [领域层] → [基础设施层]↑ ↑ ↑
Controller Service DomainFactory StrategyDTO/VO API Client
- 表示层:
OrderTemplateImportController
处理HTTP请求,负责参数校验和结果封装 - 应用层:
HotelProductCategoryFactory
实现策略路由,协调不同业务场景 - 领域层:
HotelOrderImportStrategy
定义核心业务能力,各策略实现具体导入逻辑 - 基础设施层:
HotelOrderApi
Feign客户端实现远程服务调用,ExcelUtils
处理文件解析
2. 设计模式应用
- 工厂模式:
HotelProductCategoryFactory
根据来源动态选择策略 - 策略模式:各平台导入策略实现统一接口,支持灵活扩展
- 适配器模式:通过VO/DTO转换,适配不同来源的数据结构
3. 微服务通信
二、核心代码实现分析
1. 工厂类实现
@Component
public class HotelProductCategoryFactory extends AbstractProductCategoryFactory {// 策略映射表private static final Map<String, HotelOrderImportStrategy> strategyMap = new ConcurrentHashMap<>();@PostConstructpublic void init() {strategyMap.put(FEIZHU_TYPE, feiZhuHotelOrderImportStrategy);strategyMap.put(XIECHENG_TYPE, xieChengHotelOrderImportStrategy);// ...其他策略注册}@Overridepublic HotelOrderImportStrategy getImportStrategy(String origin) {return strategyMap.getOrDefault(origin, defaultStrategy);}
}
优化点:
- 使用Map替代switch-case,提升可扩展性
- 支持默认策略,避免返回null
- 通过@PostConstruct初始化策略映射
2. 策略类核心逻辑
public class MeiTuanHotelOrderImportStrategy implements HotelOrderImportStrategy {@Overridepublic OrderImportRespVo importExcel(MultipartFile file, String origin) {// 1. 数据解析List<MeiTuanImportVo> voList = ExcelUtils.read(file, MeiTuanImportVo.class);// 2. 数据校验ValidationUtils.validate(voList);// 3. 业务处理List<HotelOrderRespDTO> createList = new ArrayList<>();List<HotelOrderRespDTO> updateList = new ArrayList<>();voList.forEach(vo -> {HotelOrderRespDTO dto = convertToDTO(vo);if (hotelOrderApi.existsOrder(dto.getOrderCode())) {updateList.add(dto);} else {createList.add(dto);}});// 4. 批量操作HotelOrderRespDTOList batchDTO = new HotelOrderRespDTOList(createList, updateList);hotelOrderApi.batchProcess(batchDTO);// 5. 构建响应return buildResult(createList, updateList);}
}
3. DTO/VO设计对比
对象类型 | 用途 | 示例字段 | 生命周期 |
VO | Excel映射 | @ExcelProperty | 请求处理阶段 |
DTO | 服务间传输 | orderCode, origin | 跨服务通信 |
Entity | 持久化对象 | id, createdAt | 数据库操作 |
三、优化建议与最佳实践
1. 性能优化
// 批量查询优化示例
public Map<String, Long> batchCheckOrderExist(List<String> orderCodes, String origin) {return hotelOrderApi.batchExistCheck(new BatchCheckQuery(orderCodes, origin));
}// 在策略类中使用
Map<String, Long> existOrders = batchCheckOrderExist(orderCodeList, origin);
2. 异常处理增强
@Slf4j
public class ImportExceptionHandler {@ExceptionHandler(ExcelReadException.class)public Result<?> handleExcelError(ExcelReadException ex) {log.error("Excel解析失败: {}", ex.getMessage());return Result.error(ErrorCode.EXCEL_PARSE_ERROR);}@ExceptionHandler(RemoteServiceException.class) public Result<?> handleRemoteError(RemoteServiceException ex) {log.error("远程服务调用失败: {}", ex.getServiceName());return Result.error(ErrorCode.REMOTE_SERVICE_UNAVAILABLE);}
}
3. 可观测性增强
// 监控埋点示例
@Aspect
@Component
public class ImportMonitorAspect {@Around("execution(* cn.iocoder..strategy.*ImportStrategy.importExcel(..))")public Object monitorImport(ProceedingJoinPoint pjp) {long start = System.currentTimeMillis();String origin = (String) pjp.getArgs()[1];try {Object result = pjp.proceed();Metrics.counter("import.requests", "origin", origin, "status", "success").increment();return result;} catch (Throwable e) {Metrics.counter("import.requests", "origin", origin, "status", "fail").increment();throw e;} finally {Metrics.timer("import.duration", "origin", origin).record(System.currentTimeMillis() - start, TimeUnit.MILLISECONDS);}}
}
4. 模板方法模式应用
public abstract class AbstractImportStrategy implements HotelOrderImportStrategy {protected final OrderImportRespVo processTemplate(MultipartFile file, String origin) {// 1. 文件校验validateFile(file);// 2. 数据解析List<?> voList = parseExcel(file);// 3. 数据转换List<HotelOrderRespDTO> dtos = convertToDTOs(voList);// 4. 业务处理(抽象方法)ProcessResult result = processBusiness(dtos, origin);// 5. 构建响应return buildResponse(result);}protected abstract ProcessResult processBusiness(List<HotelOrderRespDTO> dtos, String origin);
}// 具体策略实现
public class MeiTuanStrategy extends AbstractImportStrategy {@Overrideprotected ProcessResult processBusiness(List<HotelOrderRespDTO> dtos, String origin) {// 美团特有处理逻辑}
}
四、总结建议
- 架构扩展:
-
- 增加异步导入支持,处理大文件
- 实现断点续传功能
- 添加分布式事务支持(Seata框架)
- 代码规范:
-
- 统一异常处理规范
- 定义DTO/VO转换标准
- 完善API版本控制
- 监控告警:
-
- 关键指标监控:导入成功率、耗时、数据量
- 错误日志实时报警
- 流量控制(Sentinel集成)
- 文档完善:
-
- Swagger接口文档
- 错误代码字典
- 数据字典(订单状态映射表)
通过以上系统化设计,可以实现高可用、易扩展的酒店订单导入系统,满足多平台、高并发的业务需求。
详细扩充
以下是针对工厂模式的详细技术解析,结合酒店订单导入系统案例进行深度扩展:
一、工厂模式核心目标技术剖析
- 解耦机制实现原理
-
- 双重抽象:通过接口隔离创建者与使用者
// 抽象产品
public interface PaymentGateway {void process(PaymentRequest request);
}// 抽象工厂
public interface PaymentFactory {PaymentGateway create(String type);
}
-
- 依赖倒置:高层模块不直接依赖具体实现类
- 反射机制:动态类加载实现运行时对象创建
- 统一入口设计要点
-
- 类型注册表模式:
public class GatewayRegistry {private static Map<String, Class<? extends PaymentGateway>> mappings = new ConcurrentHashMap<>();public static void register(String type, Class<? extends PaymentGateway> clazz) {mappings.put(type, clazz);}public static PaymentGateway create(String type) {return mappings.get(type).newInstance();}
}
-
- 配置化支持:结合Spring Bean配置或YAML文件实现策略映射
二、三种工厂模式技术对比
1. 简单工厂模式实现细节
public class SimplePaymentFactory {public PaymentGateway create(String type) {switch(type) {case "ALIPAY":return new AlipayAdapter();case "WECHAT":return new WechatPayAdapter();default:throw new IllegalArgumentException("Unsupported type");}}
}
技术局限:
- 违反单一职责原则(创建逻辑集中)
- 新增类型需要修改源代码
- 难以支持复杂创建逻辑
2. 工厂方法模式进阶实现
// 抽象创建者
public abstract class PaymentProcessor {public abstract PaymentGateway createGateway();public void processOrder(Order order) {PaymentGateway gateway = createGateway();gateway.initialize(config);gateway.process(order.getAmount());}
}// 具体创建者
public class AlipayProcessor extends PaymentProcessor {@Overridepublic PaymentGateway createGateway() {return new AlipayAdapter(SSLContext.getDefault());}
}
扩展机制:
- 基于Spring的@Conditional条件化Bean创建
- 利用Java SPI服务发现机制
3. 抽象工厂模式深度应用
产品族管理实现:
public interface CloudFactory {ComputeService createCompute();StorageService createStorage();NetworkService createNetwork();
}public class AwsFactory implements CloudFactory {public ComputeService createCompute() {return new EC2Service();}public StorageService createStorage() {return new S3Service();}
}
技术优势:
- 保证跨服务兼容性(如AWS各组件使用相同认证凭证)
- 简化多云架构切换成本
三、酒店订单系统工厂模式实践
1. 策略工厂技术实现
@Component
public class ImportStrategyFactory {private final Map<String, ImportStrategy> strategies;// 基于构造器的自动注入@Autowiredpublic ImportStrategyFactory(List<ImportStrategy> strategyList) {strategies = strategyList.stream().collect(Collectors.toMap(s -> s.getClass().getAnnotation(Platform.class).value(),Function.identity()));}public ImportStrategy getStrategy(String platform) {return strategies.getOrDefault(platform, defaultStrategy);}
}
关键技术点:
- 利用Spring的List自动注入机制
- 基于注解的平台类型标记
- 线程安全的Map初始化
2. 策略模式与工厂的协同
public class CtripOrderStrategy implements ImportStrategy {private static final int BATCH_SIZE = 200;@Overridepublic ImportResult process(MultipartFile file) {List<CtripOrder> orders = parseOrders(file);return batchProcess(orders);}private ImportResult batchProcess(List<CtripOrder> orders) {List<CompletableFuture<BatchResult>> futures = new ArrayList<>();Lists.partition(orders, BATCH_SIZE).forEach(batch -> {futures.add(CompletableFuture.supplyAsync(() -> {return hotelOrderApi.batchImport(batch);}, asyncExecutor));});return combineResults(futures);}
}
性能优化点:
- 分页批处理避免内存溢出
- 异步线程池提升吞吐量
- 并行流处理加速批量操作
四、工厂模式进阶技术方案
1. 延迟初始化技术
public class LazyFactory {private ConcurrentHashMap<String, Supplier<Service>> services = new ConcurrentHashMap<>();public void register(String key, Supplier<Service> supplier) {services.put(key, supplier);}public Service getService(String key) {return services.get(key).get();}
}// 注册重型对象
factory.register("OCR", () -> new HeavyOcrService(模型文件));
2. 缓存池化实现
public class ConnectionPoolFactory {private static final int MAX_POOL_SIZE = 10;private BlockingQueue<Connection> pool = new ArrayBlockingQueue<>(MAX_POOL_SIZE);public Connection getConnection() throws InterruptedException {Connection conn = pool.poll();if (conn != null && conn.validate()) {return conn;}return createNewConnection();}private synchronized Connection createNewConnection() {if (pool.size() < MAX_POOL_SIZE) {Connection conn = new DatabaseConnection();pool.offer(conn);return conn;}throw new ConnectionPoolExhaustedException();}
}
五、工厂模式质量保障体系
1. 单元测试策略
@SpringBootTest
public class StrategyFactoryTest {@Autowiredprivate ImportStrategyFactory factory;@Testvoid testCtripStrategy() {ImportStrategy strategy = factory.getStrategy("ctrip");assertThat(strategy).isInstanceOf(CtripOrderStrategy.class);}@MockBeanprivate HotelOrderApi mockApi;@Testvoid testImportProcess() {MockMultipartFile mockFile = new MockMultipartFile(...);ImportResult result = strategy.process(mockFile);verify(mockApi, times(3)).batchImport(anyList());}
}
2. 监控指标体系
# HELP import_requests_total Total import requests
# TYPE import_requests_total counter
import_requests_total{platform="ctrip",status="success"} 238
import_requests_total{platform="meituan",status="failure"} 12# HELP import_duration_seconds Import process duration
# TYPE import_duration_seconds histogram
import_duration_seconds_bucket{platform="ctrip",le="5"} 15
import_duration_seconds_bucket{platform="ctrip",le="10"} 28
六、工厂模式演进路线
- 基础阶段:简单工厂实现核心业务隔离
- 进阶阶段:工厂方法支持多平台扩展
- 优化阶段:抽象工厂管理关联服务
- 云原生阶段:工厂+容器化部署
# 不同平台的策略实现独立容器化
services:ctrip-importer:image: strategy-ctrip:1.2env:- BATCH_SIZE=500meituan-importer:image: strategy-meituan:2.1env: - API_VERSION=v3
- Serverless阶段:基于事件触发的工厂模式
const ctripHandler = new lambda.Function(this, 'CtripHandler', {runtime: lambda.Runtime.NODEJS_14_X,handler: 'ctrip-import.handler',events: [new s3EventSource(ctripBucket, {filters: [{ suffix: '.xlsx' }]})]
});
通过以上技术方案,工厂模式可支撑从简单业务到复杂云原生架构的演进,在保证系统扩展性的同时维持高可用性。关键成功因素包括:
- 合理的抽象层次划分
- 动态注册机制的支持
- 与具体业务场景的深度结合
- 完善的监控和容错机制
- 持续演进的技术路线规划
工厂模式深度解析:从理论到实践的技术演进
一、工厂模式设计哲学深化
- 控制反转(IoC)的实现载体
// 传统方式
OrderService service = new OrderServiceImpl();// 工厂模式
OrderService service = ServiceFactory.create("order");
-
- 工厂模式是IoC原则的经典实践,将对象创建权从客户端转移到工厂
- 符合好莱坞原则:"Don't call us, we'll call you"
- 代码示例:
- 正交性设计原则
| 平台类型 \ 操作类型 | 创建订单 | 取消订单 | 修改订单 |
|-------------------|---------|---------|---------|
| 美团 | MT_CREATE | MT_CANCEL | MT_UPDATE |
| 携程 | XC_CREATE | XC_CANCEL | XC_UPDATE |
-
- 产品维度与创建逻辑解耦
- 新增产品类型不影响现有创建结构
- 产品矩阵示例:
- 类型系统的巧妙运用
interface Factory<T> {create(config: T): Product;
}class HotelFactory implements Factory<HotelConfig> {create(config: HotelConfig): HotelProduct {// 实现细节}
}
-
- 泛型工厂实现类型安全
二、酒店订单系统工厂模式实践升级
- 动态策略注册机制
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE)
public @interface PlatformStrategy {String value();
}@Component
public class StrategyRegistry {private final Map<String, ImportStrategy> strategies = new ConcurrentHashMap<>();@Autowiredpublic StrategyRegistry(ApplicationContext context) {Map<String, Object> beans = context.getBeansWithAnnotation(PlatformStrategy.class);beans.forEach((name, bean) -> {PlatformStrategy annotation = bean.getClass().getAnnotation(PlatformStrategy.class);strategies.put(annotation.value(), (ImportStrategy) bean);});}
}
- 管道-过滤器模式集成
class ImportPipeline:def __init__(self):self._filters = []def add_filter(self, filter):self._filters.append(filter)def process(self, data):for filter in self._filters:data = filter.execute(data)return dataclass ValidationFilter:def execute(self, data):# 实现验证逻辑return cleaned_data
- 反应式编程改造
public Mono<ImportResult> reactiveImport(MultipartFile file) {return Mono.fromCallable(() -> ExcelParser.parse(file)).flatMapIterable(list -> list).buffer(200).flatMap(batch -> hotelOrderApi.reactiveBatchProcess(batch)).reduce(ImportResult::combine).timeout(Duration.ofMinutes(5)).onErrorResume(e -> Mono.just(ImportResult.error(e)));
}
三、工厂模式性能优化专题
- 对象池化技术
public class ObjectPool<T> where T : new() {private ConcurrentBag<T> _objects = new();private int _maxSize = 10;public T Get() {if(_objects.TryTake(out T item)) return item;return new T();}public void Return(T item) {if(_objects.Count < _maxSize) _objects.Add(item);}
}
- 预初始化策略
@Configuration
public class PreloadConfig {@Bean@DependsOn("strategyRegistry")public ApplicationRunner preloadStrategies(StrategyRegistry registry) {return args -> {registry.getStrategy("ctrip").preloadCache();registry.getStrategy("meituan").warmUpConnection();};}
}
- JIT编译优化
public class StrategyCompiler {public ImportStrategy compileDynamicStrategy(String rules) {JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();// 动态生成策略类代码// 编译为字节码// 类加载器加载新类return dynamicInstance;}
}
四、现代化架构中的工厂模式演进
- Serverless架构适配
// AWS Lambda工厂函数
exports.handler = async (event) => {const platform = event.sourcePlatform;const strategy = require(`./strategies/${platform}`);return await strategy.process(event.records);
};
- Kubernetes Operator模式
apiVersion: factory.io/v1
kind: ImportStrategy
metadata:name: ctrip-strategy
spec:batchSize: 500timeout: 300sretryPolicy: maxAttempts: 3backoff: 2x
- AI驱动的动态工厂
class AIDrivenFactory:def __init__(self, model_path):self.model = load_ai_model(model_path)def create_strategy(self, input_data):prediction = self.model.predict(input_data)return self._select_strategy(prediction)def _select_strategy(self, features):if features['complexity'] > 0.7:return CompositeStrategy()return SimpleStrategy()
五、质量保障体系构建
- 混沌工程测试
@ChaosTest
public class StrategyChaosTest {@ChaosInjection(type = NETWORK_LATENCY, duration = 5000)void testUnderNetworkFailure() {ImportStrategy strategy = factory.getStrategy("ctrip");assertThrows(TimeoutException.class, () -> {strategy.process(largeFile);});}
}
- 契约测试
// pact-contract.json
{"provider": { "name": "HotelOrderAPI" },"consumer": { "name": "CtripStrategy" },"interactions": [{"description": "批量订单创建请求","request": { "method": "POST", "path": "/batch" },"response": { "status": 202 }}]
}
- 全链路压测
# 压测脚本示例
wrk -t12 -c400 -d300s \--script=import_script.lua \--latency http://api-gateway/import
六、工厂模式未来展望
- 量子计算适配
operation QuantumStrategySelection() : Result {using (q = Qubit()) {H(q);let result = M(q);Reset(q);return result == One ? CTripStrategy() : MeiTuanStrategy();}
}
- 区块链智能工厂
contract StrategyFactory {mapping(address => Strategy) public strategies;function createStrategy(bytes memory code) public {address addr;assembly {addr := create(0, add(code, 0x20), mload(code))}strategies[msg.sender] = Strategy(addr);}
}
- 空间计算优化
class SpatialFactory {
public:Strategy* createSpatialStrategy(GeoSpatial context) {if (context.density() > 0.8) {return new BatchProcessingStrategy();}return new RealtimeStreamingStrategy();}
};
总结演进路线
- 基础能力建设阶段
-
- 实现核心工厂模式
- 建立基础策略体系
- 完成基本质量保障
- 性能优化阶段
-
- 引入异步处理
- 实施缓存策略
- 优化内存管理
- 智能演进阶段
-
- 集成机器学习
- 实现动态策略生成
- 构建自愈系统
- 未来架构适配
-
- 量子计算准备
- 空间计算优化
- 元宇宙场景适配
通过这种阶梯式的技术演进,工厂模式可以从基础设计模式发展为支撑现代化智能系统的核心架构组件,在保持核心解耦优势的同时,不断吸收新技术成果,成为适应未来技术变革的弹性架构基础。
相关文章:
从概念和设计哲学的角度详细解析工厂模式
从概念和设计哲学的角度详细解析工厂模式。 1. 工厂模式的核心目标 解耦:将对象的创建过程与使用过程分离,使用者无需关心对象如何被创建。 统一入口:通过一个接口或方法控制对象的生成,隐藏底层实现细节。 类比现实中的工厂&am…...
AI小白:机器学习VS深度学习
1 特征工程的范式革命 传统机器学习:手工特征工程的艺术 在传统机器学习中,特征工程是一个关键步骤,它涉及将原始数据转化为能够被机器学习模型高效利用的特征。这通常需要领域专家的经验和知识,以手动设计和提取特征。 例如&a…...
对应列表数据的分割和分组
要基于指定的流派列表分割数据,可以使用 布尔索引 或 groupby 结合筛选。以下是具体方法: 场景假设 数据列 genres 中的值可能是多流派的字符串,例如 "drama,action" 或 ["drama", "action"]。目标࿱…...
信息物理系统(CPS):中国 AI(DEEPSEEK)的未来路径
一、引言 人工智能(AI)的发展正从通用模型向垂直领域渗透,而信息物理系统(CPS)作为连接数字世界与物理世界的桥梁,为 AI 提供了新的发展方向。中国 AI 企业如 DEEPSEEK 通过开源策略和本土化优势ÿ…...
SEO长尾词优化实战技巧
内容概要 长尾关键词作为SEO策略的重要组成部分,能够有效捕捉细分领域的精准流量,降低竞争成本的同时提升转化效率。本文系统梳理了从关键词挖掘到流量转化的全链路优化方法,重点解析工具使用、布局策略及搜索意图匹配三大核心模块。通过结合…...
爬虫自动化工具:DrissionPage
1. DrissionPage初始 官网地址:🛰️ 概述 | DrissionPage官网 在当今互联网高速发展的时代,网页数据的获取和处理变得愈发重要。传统的自动化工具如 Selenium 在某些方面逐渐显露出一些局限性,而 DrissionPage 正是在这样的背景下…...
扩展库Scrapy:Python网络爬虫的利器
目录 一、扩展机制的核心原理 二、六大实用扩展库详解 1. 动态渲染神器:scrapy-playwright 2. 分布式架构:scrapy-redis 3. 反反爬利器:scrapy-zyte-smartproxy 4. 智能调度:scrapy-thunder 5. 数据管道:scrapy…...
L3-21
exer01 Message # 1.定义Message消息类和cmd,content,sender,to四个属性,其中to默认为None class Message:def __init__(self, cmd, content, sender, toNone):self.cmd cmdself.content contentself.sender senderself.to to # 2. 创建登录消息对象msg1,聊天消…...
04.游戏开发-unity编辑器详细-工具栏、菜单栏、工作识图详解
04.游戏开发,unity编辑器详细-工具栏、菜单栏、工作识图详解 提示:帮帮志会陆续更新非常多的IT技术知识,希望分享的内容对您有用。本章分享的是Python基础语法。前后每一小节的内容是存在的有:学习and理解的关联性,希…...
GRBL运动控制算法(二)圆弧插补
前言 GRBL 是一款高性能、开源的嵌入式 CNC(计算机数控)控制器固件,专为 Arduino 平台优化,广泛应用于雕刻机、激光切割机、3D 打印机及其他精密运动控制场景。自 2009 年发布以来,GRBL 凭借其高效的运动规划算法、稳…...
《P1072 [NOIP 2009 提高组] Hankson 的趣味题》
题目描述 Hanks 博士是 BT(Bio-Tech,生物技术) 领域的知名专家,他的儿子名叫 Hankson。现在,刚刚放学回家的 Hankson 正在思考一个有趣的问题。 今天在课堂上,老师讲解了如何求两个正整数 c1 和 c2 的最大公约数…...
矩阵分解中的梯度下降:详细实现方案(包含数学推导、代码实现和优化技巧)
矩阵分解中的梯度下降:详细实现方案(包含数学推导、代码实现和优化技巧) 矩阵分解是机器学习和数据科学中重要的技术,广泛应用于推荐系统、自然语言处理、图像处理等领域。梯度下降作为一种优化算法,在矩阵分解中常用于最小化目标函数以找到最佳的矩阵近似。本指南将详细…...
STM32F103C8T6实现 SG90 360 °电机转动
简介 基于上一篇 STM32F103C8T6实现 SG90 180 电机任意角度转动 本来想实现角度转动, 但靠舵机本身无法实现限位, 需要记录位置, 并且根据转速计算大概位置, 存在误差, 不实现角度转动了, 只实现正反转 代码 正向速度0.75为最大速度, 反向2.25, 接近1.5…...
RTDETR融合[CVPR2025]DnLUT中的MuLUTUnit模块
RT-DETR使用教程: RT-DETR使用教程 RT-DETR改进汇总贴:RT-DETR更新汇总贴 《DnLUT: Ultra-Efficient Color Image Denoising via Channel-Aware Lookup Tables》 一、 模块介绍 论文链接:https://arxiv.org/pdf/2503.15931 代码链接…...
大数据Spark(五十七):Spark运行架构与MapReduce区别
文章目录 Spark运行架构与MapReduce区别 一、Spark运行架构 二、Spark与MapReduce区别 Spark运行架构与MapReduce区别 一、Spark运行架构 Master:Spark集群中资源管理主节点,负责管理Worker节点。Worker:Spark集群中资源管理的从节点,负责任务的运行…...
二:python基础(黑马)
一:了解 1.1: python特点 python是完全面向对象的语言 函数,模块,数字,字符串都是对象,在python中一切皆对象 完全支持继承,重载,多重继承 支持重载运算符,也支持泛型设计 py…...
【马拉车 KMP 差分数组】P6216 回文匹配|省选-
本文涉及知识点 较难理解的字符串查找算法KMP C差分数组 马拉车算法 P6216 回文匹配 题目描述 对于一对字符串 ( s 1 , s 2 ) (s_1,s_2) (s1,s2),若 s 1 s_1 s1 的长度为奇数的子串 ( l , r ) (l,r) (l,r) 满足 ( l , r ) (l,r) (l,r) 是回文的&#…...
C/C++测试框架googletest使用示例
文章目录 文档编译安装示例参考文章 文档 https://github.com/google/googletest https://google.github.io/googletest/ 编译安装 googletest是cmake项目,可以用cmake指令编译 cmake -B build && cmake --build build将编译产物lib和include 两个文件夹…...
提高MCU的效率方法
要提高MCU(微控制器单元)的编程效率,需要从硬件特性、代码优化、算法选择、资源管理等多方面入手。以下是一些关键策略: 1. 硬件相关优化 时钟与频率: 根据需求选择合适的时钟源(内部/外部振荡器),避免过高的时钟频率导致功耗浪费。关闭未使用的外设时钟(如定时器、UA…...
Ansible 实战:Roles,运维的 “魔法函数”
一、介绍 你现在已经学过tasks和handlers,那么,最好的playbook组织方式是什么呢?答案很简单:使用roles!roles基于一种已知的文件结构,能够自动加载特定的vars_files、tasks以及handlers。通过roles对内容进…...
GO简单开发grpc
什么是grpc 首先我们需要了解,什么是grpc gRPC(全称:google remote procedure call)是由Google开发的一个高性能、开源的远程过程调用(RPC)框架。它基于 HTTP/2 协议,并且使用 Protocol Buffer…...
强引用,弱引用,软引用,虚引用,自旋锁,读写锁
强引用:强引用GC不会回收 软引用:内存够的话不回收,内存不够的话回收 弱引用:不管内存够不够,只要有GC就回收 虚引用:点get是null,但是GC后他会把引用放到引用队列里边 自旋锁:是指尝…...
C++异常处理 throw try catch
C 异常处理概述 C 异常处理机制提供了一种在程序运行时捕获错误或异常情况的方式。异常处理的目的是使得程序在遇到错误时能够优雅地终止或恢复,并防止程序出现崩溃。C 使用 try, throw, 和 catch 关键字来实现异常处理。 异常处理的基本结构: throw: …...
优化 Web 性能:管理第三方资源(Third-Party Summary)
在现代 Web 开发中,第三方资源(如分析工具、广告脚本、字体服务)为网站提供了丰富的功能,但也可能成为性能瓶颈。Google 的 Lighthouse 工具在性能审计中提供了“第三方资源概要”(Third-Party Summary)&am…...
第六章、 系统级 I/O
真题考点 考点一:Unix I/O 所有的 I/O 设备(例如网络、磁盘和终端)都被模型化为文件,而所有的输入和输出都被当作对相应文件的读和写来执行。这种将设备优雅地映射为文件的方式,允许 Linux 内核引出一个简单、低级的应用接口,称为…...
Jetpack Compose 自定义标题栏终极指南:从基础到高级实战
Jetpack Compose 自定义标题栏终极指南:从基础到高级实战 本文将带你彻底掌握 Compose 标题栏开发,涵盖 5 种专业级实现方案 性能优化技巧 完整可运行代码。 📚 核心方案对比 方案特点适用场景复杂度基础Row布局完全自定义,灵…...
晶晨S905-S905L-S905LB_S905M2通刷_安卓6.0.1_16S极速开机_线刷固件包
晶晨S905-S905L-S905LB_S905M2通刷_安卓6.0.1_16S极速开机_线刷固件包 线刷方法:(新手参考借鉴一下) 刷机工具版本请用2.2.0以上,导入固件后,刷机工具右侧两个擦除打勾,然后点开始。插上刷机神器…...
tkiner模块的初步学习
文章目录 一、前言二、概念2.1 安装2.2 窗口 三、小部件3.1 概述3.2 常用小部件3.2.1 Label3.2.2 Button3.2.3 Entry3.2.4 Text3.2.5 Listbox3.2.6 Checkbutton3.2.7 Radiobutton3.2.8 Scrollbar 3.3 更多小部件3.3.1 Scale3.3.2 Spinbox3.3.3. Progressbar 3.4 主题小部件 四、…...
Java常用数据结构操作方法全面总结
目录 一、List接口及其实现类二、Set接口及其实现类三、Map接口及其实现类四、Queue/Deque队列五、Stack栈六、树形结构七、注意事项与最佳实践总结 一、List接口及其实现类 核心实现类 ArrayList:基于动态数组LinkedList:基于双向链表 常用操作方法…...
Java的Selenium的特殊元素操作与定位之select下拉框
如果页面元素是一个下拉框,我们可以将此web元素封装为Select对象 Select selectnew Select(WebElement element); Select对象常用api select.getOptions();//获取所有选项select.selectBylndex(index);//根据索引选中对应的元素select.selectByValue(value);//选…...
STM32单片机入门学习——第15节: [6-3] TIM输出比较
写这个文章是用来学习的,记录一下我的学习过程。希望我能一直坚持下去,我只是一个小白,只是想好好学习,我知道这会很难,但我还是想去做! 本文写于:2025.04.05 STM32开发板学习——第15节: [6-3] TIM输出比较 前言开发板说明引用解答和科普一…...
力扣经典算法篇-9-跳跃游戏(贪心算法,反向递推)
题干: 给你一个非负整数数组 nums ,你最初位于数组的 第一个下标 。数组中的每个元素代表你在该位置可以跳跃的最大长度。 判断你是否能够到达最后一个下标,如果可以,返回 true ;否则,返回 false 。 示例 …...
java面向对象 - 封装、继承和多态
1.封装 定义 封装是把对象的属性和操作(或服务)结合为一个独立的整体,并尽可能隐藏对象的内部实现细节。通过访问控制修饰符(如private、protected、public)对属性和方法的访问进行限制,以此提升代码的安全性与可维护性。 要点 访问控制:运用private修饰属性,防止外部直…...
铁电液晶(FLC)与反铁电液晶(AFLC)
### **铁电液晶(FLC)与反铁电液晶(AFLC)的原理、区别及应用** --- ## **1. 基本原理** ### **(1)铁电液晶(Ferroelectric Liquid Crystal, FLC)** - **分子结构**: …...
经典算法 a^b
原题目链接 问题描述 求 a 的 b 次方对 p 取模的值,即计算: a^b mod p输入格式 输入一行,包含三个整数 a、b 和 p,中间用空格隔开。 输出格式 输出一个整数,表示 a^b mod p 的值。 数据范围 0 ≤ a, b ≤ 10^91 …...
Python解决“组成字符串ku的最大次数”问题
Python解决“组成字符串ku的最大次数”问题 问题描述测试样例解题思路代码 问题描述 给定一个字符串 s,该字符串中只包含英文大小写字母。你需要计算从字符串中最多能组成多少个字符串 “ku”。每次可以随机从字符串中选一个字符,并且选中的字符不能再使…...
ubuntu22使用TrinityCore搭建魔兽世界服务器
目录 一、Ubuntu22工具下载二、服务端编译配置1. 从 git 上拉取服务端代码2. 编译客户端3. 修改配置文件4. 加载sql语句5. 下载客户端6. 下载必要sql文件 三、客户端连接配置四、游戏启动 一、Ubuntu22工具下载 下载所有需要的工具 sudo apt-get update sudo apt-get install…...
LeetCode - 739.每日温度问题单调栈解法
目录 问题描述 方法思路:单调栈 核心思想 为什么用单调栈? 算法步骤 代码实现与逐行解析 示例解析 复杂度分析 总结 问题描述 给定一个整数数组 temperatures,表示每天的温度,返回一个数组 answer,其中 answe…...
GESP:2025-3月等级8-T1-上学
时间限制 : 1 秒 内存限制 : 128 MB C 城可以视为由 n个结点与 m条边组成的无向图。这些结点依次以1,2,....n标号,边依次以 1,2...m标号。第i条边(1<i<m )连接编号为ui 与vi的结点,长度为li米。 小 A 的学校坐落在 C 城中…...
宏碁笔记本电脑擎7PRO搭载的 NVIDIA RTX 5080 显卡安装pytorch
宏碁笔记本电脑擎7PRO搭载的 NVIDIA RTX 5080 显卡是一款高性能移动 GPU,基于 NVIDIA 最新的 Blackwell 架构设计,通过修正架构(Blackwell)、显存类型与带宽(GDDR7、960GB/s)、Tensor Core 与 RT Core 全面…...
Qwen-7B-Chat 本地化部署使用
通义千问 简介 通义千问是阿里云推出的超大规模语言模型,以下是其优缺点: 优点 强大的基础能力:具备语义理解与抽取、闲聊、上下文对话、生成与创作、知识与百科、代码、逻辑与推理、计算、角色扮演等多种能力。可以续写小说、编写邮件、解…...
数据结构,顺序存储线性表
//线性表顺序存储 #include<stdio.h> #include<stdlib.h> #define MAXSIZE 100 #define ElemType int //定义结构体 typedef struct LinearList{ElemType elem[MAXSIZE];int last; }LinearList; //初始化链表 void InitList(LinearList &L){L.last-1; };…...
Matlab轴承故障信号仿真与故障分析
1.摘要 本文介绍了一个基于Matlab的轴承故障信号仿真与分析程序,旨在模拟和分析轴承内圈故障信号的特征。程序首先通过生成故障信号、共振信号和调制信号,添加噪声和离散化处理,构建模拟的振动信号,并保存相关数据。通过快速傅里…...
Git三剑客:工作区、暂存区、版本库深度解析
一、引言:为什么需要理解Git的核心区域? 作为开发者,Git是日常必备的版本控制工具。但你是否曾因以下问题感到困惑? 修改了文件,但 git status 显示一片混乱? git add 和 git commit 到底做了什么&#x…...
stack和queue
1.stack的使用 函数说明接口说明 stack() 构造空的栈 empty 检测stack是否为空 size 返回stack中元素的个数 top 返回栈顶元素的引用 push 将元素val压入stack中 pop 将stack中尾部的元素弹出 void test_stack() {stack<int> st;st.push(1);st.push(2);st.push(3);s…...
【补题】Codeforces Round 1011 (Div. 2) C. Serval and The Formula
题意:给两个数,问你存不存在k使nmn异或m 思路: 为了让nmn异或m成功,很明显有两个数在同一位上最多只能有1个1。因为如果有两个就会导致数字变小,很明显nm是不可能成功的,因为你怎么搞都会有至少一个一模一…...
基于javaweb的SpringBoot汉服文化bbs系统设计与实现(源码+文档+部署讲解)
技术范围:SpringBoot、Vue、SSM、HLMT、Jsp、PHP、Nodejs、Python、爬虫、数据可视化、小程序、安卓app、大数据、物联网、机器学习等设计与开发。 主要内容:免费功能设计、开题报告、任务书、中期检查PPT、系统功能实现、代码编写、论文编写和辅导、论文…...
Vision_Robot
import time import tkinter as tk from tkinter import messagebox from PIL import Image, ImageTk import socket import threading from datetime import datetime import logging import subprocess # 确保导入 subprocess 库 import os import pyautogu…...
爬虫练习案例
案例1: 爬取菜鸟教程左侧导航栏的分类内容: 在pycharm中书写代码。 先倒入相关模块。 import requests from bs4 import BeautifulSoup import lxml.etree as le这个案例写两种写法。 第一种: urlhttps://www.runoob.com/html/html-tuto…...
大数据时代的隐私保护:区块链技术的创新应用
一、引言 在当今数字化时代,大数据已经成为推动社会发展的关键力量。从商业决策到社会治理,从医疗健康到金融服务,数据的价值日益凸显。然而,随着数据的大量收集和广泛使用,隐私保护问题也日益突出。如何在充分利用大…...