【PostgreSQL 03】PostGIS空间数据深度实战:从地图服务到智慧城市

article/2025/6/19 6:00:37

PostGIS空间数据深度实战:从地图服务到智慧城市

关键词
PostGIS, 空间数据库, 地理信息系统, GIS, 空间查询, 地理分析, 位置服务, 智慧城市, 空间索引, 坐标系统

摘要
PostGIS是PostgreSQL的空间数据扩展,它将普通的关系数据库转变为强大的地理信息系统。本文将从零开始,通过生动的实例和通俗易懂的语言,带你掌握PostGIS的核心概念和实战技能。从简单的地图服务到复杂的智慧城市应用,从基础的空间查询到高级的地理分析,我们将一步步构建完整的空间数据解决方案。无论你是想要开发LBS应用,还是要构建城市管理系统,这篇文章都将为你提供扎实的技术基础。


引言:当数据库遇上地图

想象一下这样的场景:

你正在开发一个外卖平台,产品经理提出了这些需求:

  • “用户下单时,自动推荐附近2公里内的餐厅”
  • “配送员接单后,计算最优配送路线”
  • “分析哪些区域订单密度最高,方便商家选址”
  • “实时监控配送员位置,预估送达时间”

如果用传统的关系数据库,你可能会这样处理:

-- 传统方案:用三角函数计算距离
SELECT restaurant_name,SQRT(POW(lat - 39.9042, 2) + POW(lng - 116.4074, 2)) as distance
FROM restaurants 
WHERE SQRT(POW(lat - 39.9042, 2) + POW(lng - 116.4074, 2)) < 0.02
ORDER BY distance;

但这种方案有什么问题呢?

  • 计算不准确(地球是球体,不是平面)
  • 性能很差(无法使用索引)
  • 功能有限(无法处理复杂的地理关系)
  • 扩展困难(新增地理功能需要大量代码)

PostGIS就是为了解决这些问题而生的。它让数据库原生支持地理数据,就像支持数字和文本一样自然。

在这里插入图片描述

第一部分:PostGIS基础 - 让数据库理解地理世界

什么是PostGIS?

PostGIS可以理解为PostgreSQL的"地理大脑"。它为数据库添加了:

  1. 空间数据类型:点、线、面等几何对象
  2. 空间函数:距离计算、相交判断等地理运算
  3. 空间索引:高效的地理查询性能
  4. 坐标系统:支持全球各种地图投影

安装和启用PostGIS

-- 安装PostGIS扩展
CREATE EXTENSION postgis;-- 查看PostGIS版本
SELECT PostGIS_Version();-- 查看支持的空间参考系统
SELECT srid, proj4text FROM spatial_ref_sys LIMIT 5;

核心空间数据类型

PostGIS提供了丰富的空间数据类型,就像几何学中的基本图形:

1. POINT(点)

-- 创建点几何
SELECT ST_GeomFromText('POINT(116.4074 39.9042)', 4326) as beijing_center;-- 从经纬度创建点
SELECT ST_Point(116.4074, 39.9042) as point_geom;

2. LINESTRING(线)

-- 创建线几何(道路、路径)
SELECT ST_GeomFromText('LINESTRING(116.40 39.90, 116.41 39.91, 116.42 39.92)', 4326) as road;

3. POLYGON(面)

-- 创建多边形(区域、边界)
SELECT ST_GeomFromText('POLYGON((116.40 39.90, 116.41 39.90, 116.41 39.91, 116.40 39.91, 116.40 39.90))', 4326) as area;

坐标系统:地球不是平的

这是PostGIS中最重要但也最容易被忽视的概念。想象一下:

  • 地理坐标系(如WGS84,SRID 4326):就像地球仪上的经纬度
  • 投影坐标系(如UTM):就像把地球仪摊平成地图
-- WGS84地理坐标系(经纬度)
SELECT ST_GeomFromText('POINT(116.4074 39.9042)', 4326) as wgs84_point;-- 转换为投影坐标系(米为单位)
SELECT ST_Transform(ST_GeomFromText('POINT(116.4074 39.9042)', 4326), 3857) as web_mercator;

第二部分:空间查询实战 - 掌握地理关系分析

在这里插入图片描述

实战案例:构建外卖配送系统

让我们构建一个完整的外卖配送系统,学习各种空间查询:

-- 创建餐厅表
CREATE TABLE restaurants (id SERIAL PRIMARY KEY,name VARCHAR(100),location GEOMETRY(POINT, 4326),delivery_radius INTEGER DEFAULT 3000, -- 配送半径(米)cuisine_type VARCHAR(50),rating DECIMAL(3,2)
);-- 创建用户表
CREATE TABLE users (id SERIAL PRIMARY KEY,name VARCHAR(100),current_location GEOMETRY(POINT, 4326),address TEXT
);-- 创建配送员表
CREATE TABLE drivers (id SERIAL PRIMARY KEY,name VARCHAR(100),current_location GEOMETRY(POINT, 4326),is_available BOOLEAN DEFAULT true,vehicle_type VARCHAR(20)
);-- 插入测试数据
INSERT INTO restaurants (name, location, delivery_radius, cuisine_type, rating) VALUES 
('老北京炸酱面', ST_Point(116.4551, 39.9380, 4326), 2000, '中餐', 4.5),
('麦当劳', ST_Point(116.4579, 39.9081, 4326), 3000, '快餐', 4.2),
('海底捞', ST_Point(116.3105, 39.9830, 4326), 5000, '火锅', 4.8);INSERT INTO users (name, current_location, address) VALUES 
('张三', ST_Point(116.4520, 39.9350, 4326), '三里屯SOHO'),
('李四', ST_Point(116.3100, 39.9800, 4326), '中关村大街');INSERT INTO drivers (name, current_location, vehicle_type) VALUES 
('王师傅', ST_Point(116.4500, 39.9300, 4326), '电动车'),
('赵师傅', ST_Point(116.3150, 39.9820, 4326), '摩托车');

核心空间查询操作

1. 距离查询 - ST_DWithin

-- 查找用户附近2公里内的餐厅
SELECT r.name,r.cuisine_type,r.rating,ST_Distance(r.location, u.current_location) as distance_meters
FROM restaurants r,users u
WHERE u.name = '张三'AND ST_DWithin(r.location, u.current_location, 2000)
ORDER BY distance_meters;

2. 包含查询 - ST_Contains

-- 创建配送区域
CREATE TABLE delivery_zones (id SERIAL PRIMARY KEY,zone_name VARCHAR(100),boundary GEOMETRY(POLYGON, 4326),delivery_fee DECIMAL(10,2)
);-- 插入配送区域
INSERT INTO delivery_zones (zone_name, boundary, delivery_fee) VALUES 
('市中心区', ST_GeomFromText('POLYGON((116.35 39.85, 116.50 39.85, 116.50 39.95, 116.35 39.95, 116.35 39.85))', 4326), 5.00);-- 查找用户所在的配送区域
SELECT u.name,dz.zone_name,dz.delivery_fee
FROM users u
JOIN delivery_zones dz ON ST_Contains(dz.boundary, u.current_location);

3. 最近邻查询 - ST_Distance + ORDER BY

-- 为订单分配最近的配送员
WITH order_location AS (SELECT ST_Point(116.4550, 39.9370, 4326) as location
)
SELECT d.name,d.vehicle_type,ST_Distance(d.current_location, ol.location) as distance
FROM drivers d,order_location ol
WHERE d.is_available = true
ORDER BY distance
LIMIT 1;

4. 相交查询 - ST_Intersects

-- 查找与配送路线相交的区域
CREATE TABLE traffic_zones (id SERIAL PRIMARY KEY,zone_name VARCHAR(100),boundary GEOMETRY(POLYGON, 4326),traffic_level VARCHAR(20)
);-- 配送路线
WITH delivery_route AS (SELECT ST_MakeLine(ARRAY[ST_Point(116.4551, 39.9380, 4326),  -- 餐厅ST_Point(116.4520, 39.9350, 4326)   -- 用户]) as route
)
SELECT tz.zone_name,tz.traffic_level
FROM traffic_zones tz,delivery_route dr
WHERE ST_Intersects(tz.boundary, dr.route);

第三部分:高级空间分析 - 构建智能决策系统

缓冲区分析

缓冲区就像在地图上画圆圈,用于分析影响范围:

-- 分析餐厅配送覆盖范围
SELECT r.name,ST_Buffer(r.location, r.delivery_radius) as coverage_area
FROM restaurants r;-- 查找配送覆盖范围重叠的餐厅
SELECT r1.name as restaurant1,r2.name as restaurant2,ST_Area(ST_Intersection(ST_Buffer(r1.location, r1.delivery_radius),ST_Buffer(r2.location, r2.delivery_radius))) as overlap_area
FROM restaurants r1,restaurants r2
WHERE r1.id < r2.idAND ST_Intersects(ST_Buffer(r1.location, r1.delivery_radius),ST_Buffer(r2.location, r2.delivery_radius));

热力图分析

分析订单密度分布,帮助商家选址:

-- 创建订单表
CREATE TABLE orders (id SERIAL PRIMARY KEY,user_id INTEGER REFERENCES users(id),restaurant_id INTEGER REFERENCES restaurants(id),delivery_location GEOMETRY(POINT, 4326),order_time TIMESTAMP DEFAULT NOW(),total_amount DECIMAL(10,2)
);-- 网格化热力图分析
WITH order_grid AS (SELECT ST_SnapToGrid(delivery_location, 0.01) as grid_cell,  -- 创建1km网格COUNT(*) as order_count,AVG(total_amount) as avg_amountFROM ordersWHERE order_time >= NOW() - INTERVAL '30 days'GROUP BY ST_SnapToGrid(delivery_location, 0.01)
)
SELECT ST_X(grid_cell) as longitude,ST_Y(grid_cell) as latitude,order_count,avg_amount,CASE WHEN order_count > 100 THEN '热点区域'WHEN order_count > 50 THEN '活跃区域'ELSE '一般区域'END as area_type
FROM order_grid
WHERE order_count > 10
ORDER BY order_count DESC;

路径分析

计算最优配送路线:

-- 简化的路径分析(实际应用中需要路网数据)
CREATE OR REPLACE FUNCTION calculate_delivery_route(restaurant_point GEOMETRY,user_point GEOMETRY
) RETURNS TABLE(route_geometry GEOMETRY,distance_km DECIMAL,estimated_time_minutes INTEGER
) AS $$
BEGINRETURN QUERYSELECT ST_MakeLine(restaurant_point, user_point) as route_geometry,ROUND(ST_Distance(restaurant_point, user_point)::DECIMAL / 1000, 2) as distance_km,ROUND(ST_Distance(restaurant_point, user_point) / 500)::INTEGER as estimated_time_minutes; -- 假设500米/分钟
END;
$$ LANGUAGE plpgsql;-- 使用路径分析函数
SELECT * FROM calculate_delivery_route(ST_Point(116.4551, 39.9380, 4326),  -- 餐厅位置ST_Point(116.4520, 39.9350, 4326)   -- 用户位置
);

第四部分:智慧城市应用 - 大规模空间数据处理

在这里插入图片描述

交通流量分析系统

-- 创建交通监测点表
CREATE TABLE traffic_sensors (id SERIAL PRIMARY KEY,sensor_name VARCHAR(100),location GEOMETRY(POINT, 4326),road_segment_id INTEGER,sensor_type VARCHAR(50)
);-- 创建交通流量数据表
CREATE TABLE traffic_data (id SERIAL PRIMARY KEY,sensor_id INTEGER REFERENCES traffic_sensors(id),timestamp TIMESTAMP,vehicle_count INTEGER,average_speed DECIMAL(5,2),congestion_level VARCHAR(20)
);-- 实时交通流量分析
WITH current_traffic AS (SELECT ts.sensor_name,ts.location,td.vehicle_count,td.average_speed,td.congestion_level,ST_Buffer(ts.location, 500) as influence_area  -- 500米影响范围FROM traffic_sensors tsJOIN traffic_data td ON ts.id = td.sensor_idWHERE td.timestamp >= NOW() - INTERVAL '5 minutes'
),
congestion_areas AS (SELECT ST_Union(influence_area) as congested_areaFROM current_trafficWHERE congestion_level = '拥堵'
)
-- 查找受拥堵影响的配送路线
SELECT o.id as order_id,ST_Length(ST_Intersection(ST_MakeLine(r.location, o.delivery_location),ca.congested_area)) as affected_route_length
FROM orders o
JOIN restaurants r ON o.restaurant_id = r.id,congestion_areas ca
WHERE o.order_time >= NOW() - INTERVAL '1 hour'AND ST_Intersects(ST_MakeLine(r.location, o.delivery_location),ca.congested_area);

环境监测与分析

-- 创建环境监测站表
CREATE TABLE environmental_stations (id SERIAL PRIMARY KEY,station_name VARCHAR(100),location GEOMETRY(POINT, 4326),station_type VARCHAR(50)
);-- 创建环境数据表
CREATE TABLE environmental_data (id SERIAL PRIMARY KEY,station_id INTEGER REFERENCES environmental_stations(id),timestamp TIMESTAMP,pm25_value DECIMAL(6,2),temperature DECIMAL(4,1),humidity DECIMAL(4,1),noise_level DECIMAL(4,1)
);-- 空气质量影响分析
WITH pollution_sources AS (SELECT es.location,ed.pm25_value,-- 根据PM2.5值计算影响半径CASE WHEN ed.pm25_value > 75 THEN 2000WHEN ed.pm25_value > 35 THEN 1000ELSE 500END as influence_radiusFROM environmental_stations esJOIN environmental_data ed ON es.id = ed.station_idWHERE ed.timestamp >= NOW() - INTERVAL '1 hour'AND ed.pm25_value > 35  -- 轻度污染以上
)
-- 分析受空气污染影响的餐厅
SELECT r.name,r.location,ps.pm25_value,ST_Distance(r.location, ps.location) as distance_to_pollution
FROM restaurants r,pollution_sources ps
WHERE ST_DWithin(r.location, ps.location, ps.influence_radius)
ORDER BY ps.pm25_value DESC, distance_to_pollution;

应急响应系统

-- 创建应急事件表
CREATE TABLE emergency_events (id SERIAL PRIMARY KEY,event_type VARCHAR(50),location GEOMETRY(POINT, 4326),severity_level INTEGER, -- 1-5级event_time TIMESTAMP DEFAULT NOW(),description TEXT,status VARCHAR(20) DEFAULT 'active'
);-- 创建应急资源表
CREATE TABLE emergency_resources (id SERIAL PRIMARY KEY,resource_type VARCHAR(50), -- 消防车、救护车、警车current_location GEOMETRY(POINT, 4326),is_available BOOLEAN DEFAULT true,capacity INTEGER
);-- 应急响应资源调度
CREATE OR REPLACE FUNCTION emergency_response(event_location GEOMETRY,event_severity INTEGER
) RETURNS TABLE(resource_id INTEGER,resource_type VARCHAR,distance_km DECIMAL,estimated_arrival_minutes INTEGER,priority_score DECIMAL
) AS $$
DECLAREresponse_radius INTEGER;
BEGIN-- 根据事件严重程度确定响应半径response_radius := event_severity * 2000; -- 每级2公里RETURN QUERYSELECT er.id,er.resource_type,ROUND(ST_Distance(er.current_location, event_location)::DECIMAL / 1000, 2),ROUND(ST_Distance(er.current_location, event_location) / 800)::INTEGER, -- 假设800米/分钟-- 优先级评分:距离越近、容量越大分数越高ROUND((10000 - ST_Distance(er.current_location, event_location)) / 100 + er.capacity, 2)FROM emergency_resources erWHERE er.is_available = trueAND ST_DWithin(er.current_location, event_location, response_radius)ORDER BY priority_score DESC;
END;
$$ LANGUAGE plpgsql;-- 使用应急响应函数
SELECT * FROM emergency_response(ST_Point(116.4074, 39.9042, 4326),  -- 天安门广场4  -- 4级严重事件
);

第五部分:性能优化与最佳实践

空间索引优化

-- 创建空间索引
CREATE INDEX idx_restaurants_location ON restaurants USING GIST (location);
CREATE INDEX idx_users_location ON users USING GIST (current_location);
CREATE INDEX idx_drivers_location ON drivers USING GIST (current_location);-- 查看索引使用情况
EXPLAIN (ANALYZE, BUFFERS) 
SELECT * FROM restaurants 
WHERE ST_DWithin(location, ST_Point(116.4074, 39.9042, 4326), 2000);

数据分区策略

-- 按地理区域分区
CREATE TABLE orders_partitioned (id SERIAL,user_id INTEGER,restaurant_id INTEGER,delivery_location GEOMETRY(POINT, 4326),order_time TIMESTAMP,region_code INTEGER
) PARTITION BY RANGE (region_code);-- 创建分区表
CREATE TABLE orders_beijing PARTITION OF orders_partitionedFOR VALUES FROM (1100) TO (1200);CREATE TABLE orders_shanghai PARTITION OF orders_partitionedFOR VALUES FROM (3100) TO (3200);

查询优化技巧

-- 1. 使用边界框预过滤
SELECT * FROM restaurants 
WHERE location && ST_MakeEnvelope(116.3, 39.8, 116.5, 40.0, 4326)  -- 边界框过滤AND ST_DWithin(location, ST_Point(116.4074, 39.9042, 4326), 2000); -- 精确距离过滤-- 2. 避免不必要的坐标转换
-- 好的做法:在同一坐标系中计算
SELECT ST_Distance(location1, location2) FROM table_name;
-- 不好的做法:频繁转换坐标系
SELECT ST_Distance(ST_Transform(location1, 3857), ST_Transform(location2, 3857)) FROM table_name;-- 3. 使用合适的几何类型
-- 对于简单的圆形范围查询,使用ST_DWithin而不是ST_Buffer + ST_Contains
SELECT * FROM restaurants 
WHERE ST_DWithin(location, user_location, 2000);  -- 推荐-- 而不是
SELECT * FROM restaurants 
WHERE ST_Contains(ST_Buffer(user_location, 2000), location);  -- 不推荐

第六部分:实战项目:智能配送优化系统

让我们整合所有知识,构建一个完整的智能配送优化系统:

-- 创建综合配送优化函数
CREATE OR REPLACE FUNCTION optimize_delivery_assignment(user_location GEOMETRY,max_distance INTEGER DEFAULT 5000
) RETURNS TABLE(restaurant_id INTEGER,restaurant_name VARCHAR,driver_id INTEGER,driver_name VARCHAR,total_distance DECIMAL,estimated_time INTEGER,optimization_score DECIMAL
) AS $$
BEGINRETURN QUERYWITH available_restaurants AS (SELECT r.id,r.name,r.location,r.rating,ST_Distance(r.location, user_location) as distance_to_userFROM restaurants rWHERE ST_DWithin(r.location, user_location, max_distance)),available_drivers AS (SELECT d.id,d.name,d.current_location,d.vehicle_typeFROM drivers dWHERE d.is_available = true),delivery_combinations AS (SELECT ar.id as restaurant_id,ar.name as restaurant_name,ad.id as driver_id,ad.name as driver_name,ar.distance_to_user,ST_Distance(ad.current_location, ar.location) as driver_to_restaurant,ar.rating,CASE ad.vehicle_type WHEN '摩托车' THEN 1.5 WHEN '电动车' THEN 1.0 ELSE 0.8 END as speed_factorFROM available_restaurants arCROSS JOIN available_drivers ad)SELECT dc.restaurant_id,dc.restaurant_name,dc.driver_id,dc.driver_name,ROUND((dc.driver_to_restaurant + dc.distance_to_user)::DECIMAL / 1000, 2),ROUND((dc.driver_to_restaurant + dc.distance_to_user) / (500 * dc.speed_factor))::INTEGER,-- 综合评分:考虑距离、餐厅评分、配送效率ROUND((10 - (dc.driver_to_restaurant + dc.distance_to_user) / 1000) * 0.4 +  -- 距离权重40%dc.rating * 0.3 +  -- 餐厅评分权重30%dc.speed_factor * 2 * 0.3,  -- 配送效率权重30%2)FROM delivery_combinations dcORDER BY optimization_score DESCLIMIT 10;
END;
$$ LANGUAGE plpgsql;-- 使用优化函数
SELECT * FROM optimize_delivery_assignment(ST_Point(116.4520, 39.9350, 4326),  -- 用户位置3000  -- 最大搜索距离3公里
);

实时监控仪表板

-- 创建实时监控视图
CREATE OR REPLACE VIEW delivery_dashboard AS
WITH real_time_stats AS (SELECT COUNT(*) as total_orders,COUNT(*) FILTER (WHERE order_time >= NOW() - INTERVAL '1 hour') as orders_last_hour,AVG(ST_Distance(r.location, o.delivery_location)) as avg_delivery_distance,COUNT(DISTINCT d.id) FILTER (WHERE d.is_available = true) as available_driversFROM orders oJOIN restaurants r ON o.restaurant_id = r.idLEFT JOIN drivers d ON trueWHERE o.order_time >= NOW() - INTERVAL '24 hours'
),
busy_areas AS (SELECT ST_SnapToGrid(delivery_location, 0.01) as grid_cell,COUNT(*) as order_densityFROM ordersWHERE order_time >= NOW() - INTERVAL '2 hours'GROUP BY ST_SnapToGrid(delivery_location, 0.01)ORDER BY order_density DESCLIMIT 5
)
SELECT rts.*,json_agg(json_build_object('longitude', ST_X(ba.grid_cell),'latitude', ST_Y(ba.grid_cell),'order_count', ba.order_density)) as hot_spots
FROM real_time_stats rts,busy_areas ba
GROUP BY rts.total_orders, rts.orders_last_hour, rts.avg_delivery_distance, rts.available_drivers;-- 查看实时监控数据
SELECT * FROM delivery_dashboard;

总结:PostGIS的空间数据革命

通过这篇文章的学习,我们从零开始构建了一个完整的空间数据应用系统。让我们回顾一下PostGIS的核心价值:

技术优势总结

  1. 原生空间支持:数据库级别的地理数据处理
  2. 标准兼容:支持OGC标准,与各种GIS工具兼容
  3. 高性能:空间索引和优化算法保证查询效率
  4. 功能丰富:数百个空间函数覆盖各种应用场景
  5. 扩展性强:可以处理从简单LBS到复杂GIS的各种需求

应用场景回顾

应用领域核心功能关键技术
位置服务附近搜索、路径规划ST_DWithin, ST_Distance
智慧城市交通分析、环境监测空间聚合、热力图分析
物流配送路线优化、区域管理缓冲区分析、网络分析
应急响应资源调度、影响评估最近邻查询、空间关系

最佳实践指南

  1. 合理选择坐标系:地理坐标系用于存储,投影坐标系用于计算
  2. 创建空间索引:所有空间字段都应该有GIST索引
  3. 优化查询策略:使用边界框预过滤,避免不必要的坐标转换
  4. 数据分区管理:大规模数据按地理区域分区
  5. 监控性能指标:定期分析查询性能,优化慢查询

发展趋势展望

PostGIS正在向更智能、更高效的方向发展:

  • 3D空间分析:支持三维地理数据处理
  • 时空数据:集成时间维度的空间分析
  • 机器学习集成:空间数据的AI分析能力
  • 实时流处理:支持实时地理数据流分析
  • 云原生优化:更好的云环境性能表现

PostGIS不仅仅是一个数据库扩展,它是连接现实世界与数字世界的桥梁。无论你是在开发下一个独角兽级别的LBS应用,还是在构建智慧城市的基础设施,PostGIS都将是你最可靠的技术伙伴。

下一篇预告:《PostgreSQL性能调优深度实战:从查询优化到服务器配置》

我们将深入探讨PostgreSQL的性能优化技巧,从SQL查询优化到服务器参数调优,从索引策略到连接池配置,帮你构建高性能的数据库系统。


如果这篇文章对你有帮助,欢迎点赞、收藏和分享。有任何问题或建议,欢迎在评论区讨论!


http://www.hkcw.cn/article/djMmnxZLEO.shtml

相关文章

Wireshark 使用教程:让抓包不再神秘

一、什么是 tshark&#xff1f; tshark 是 Wireshark 的命令行版本&#xff0c;支持几乎所有 Wireshark 的核心功能。它可以用来&#xff1a; 抓包并保存为 pcap 文件 实时显示数据包信息 提取指定字段进行分析 配合 shell 脚本完成自动化任务 二、安装与验证 Kali Linux…

环境变量Path单行显示改回多行列表显示

环境变量Path单行显示改回多行列表显示 今天去配置环境变量时&#xff0c;双击Path竟然只显示一行&#xff0c;明明记得上次还时一个列表显示来着。由于以前有删除了所有Path变量的经历&#xff0c;所以看到这个情况属实吓我一跳且一脸懵。 仔细地看了一下&#xff0c;Path中…

CodeTop100 Day18

52、最长的有效括号 括号问题需要考虑栈&#xff0c;而最长有效的括号就要考虑动态规划了 这里定义dp[i]为以i-1位置结尾的最长合法括号字串 遍历字符串&#xff0c;当遇到左括号&#xff0c;压入栈&#xff0c;dp[i1]0,遇到右括号&#xff0c;如果栈不为空&#xff0c;配对左…

NLP基础:从词嵌入到预训练模型应用

NLP基础&#xff1a;从词嵌入到预训练模型应用 系统化学习人工智能网站&#xff08;收藏&#xff09;&#xff1a;https://www.captainbed.cn/flu 文章目录 NLP基础&#xff1a;从词嵌入到预训练模型应用摘要引言一、词嵌入技术&#xff1a;从离散到连续的语义表示1. 传统词嵌…

STM32CubeMX串口配置

STM32CubeMX串口配置 一&#xff0c;Mode1&#xff0c;Asynchronous&#xff08;异步模式&#xff09;2&#xff0c;其他模式3&#xff0c;异步通信中的流控 二&#xff0c;Configuration参数配置(Parameter Settings)1&#xff0c;Basic Parameters2&#xff0c;Advanced Para…

Java内存模型(JMM)与多线程编程实战

最近正在复习Java八股&#xff0c;所以会将一些热门的八股问题&#xff0c;结合ai与自身理解写成博客便于记忆 今天将以这四个问题为依据。 一、JMM内存模型解析 1. JMM核心概念 Java内存模型(Java Memory Model)定义了Java程序中各种变量&#xff08;线程共享变量&#xf…

Spring Cache核心原理与快速入门指南

文章目录 前言一、Spring Cache核心原理1.1 架构设计思想1.2 运行时执行流程1.3 核心组件协作1.4 关键机制详解1.5 扩展点设计1.6 与Spring事务的协同 二、快速入门实战三、局限性3.1 多级缓存一致性缺陷3.2 分布式锁能力缺失3.3 事务集成陷阱 总结 前言 在当今高并发、低延迟…

【设计模式-4.5】行为型——迭代器模式

说明&#xff1a;本文介绍设计模式中&#xff0c;行为型设计模式之一的迭代器模式。 定义 迭代器模式&#xff08;Iterator Pattern&#xff09;&#xff0c;也叫作游标模式&#xff08;Cursor Pattern&#xff09;&#xff0c;它提供一种按顺序访问集合/容器对象元素的方法&…

【Python训练营打卡】day40 @浙大疏锦行

DAY 40 训练和测试的规范写法 知识点回顾&#xff1a; 1. 彩色和灰度图片测试和训练的规范写法&#xff1a;封装在函数中 2. 展平操作&#xff1a;除第一个维度batchsize外全部展平 3. dropout操作&#xff1a;训练阶段随机丢弃神经元&#xff0c;测试阶段eval模式关闭dropo…

软件技术如何赚钱

1. 开发并销售软件产品​ ​ 独立应用开发&#xff1a;针对特定需求或市场痛点&#xff0c;开发移动应用、桌面软件或网页应用。例如&#xff0c;开发一款专注于时间管理的移动应用&#xff0c;帮助用户提高工作效率。以 Python 结合 Kivy 框架开发一个简单的待办事项应用为例…

【Github/Gitee Webhook触发自动部署-Jenkins】

Github/Gitee Webhook触发自动部署-Jenkins #mermaid-svg-ryhZQMOzmkQZNMwX {font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}#mermaid-svg-ryhZQMOzmkQZNMwX .error-icon{fill:#552222;}#mermaid-svg-ryhZQMOzmkQZNMwX .error-tex…

华为OD机试真题——最小的调整次数/特异性双端队列(2025A卷:100分)Java/python/JavaScript/C++/C语言/GO六种最佳实现

2025 A卷 100分 题型 本文涵盖详细的问题分析、解题思路、代码实现、代码详解、测试用例以及综合分析; 并提供Java、python、JavaScript、C++、C语言、GO六种语言的最佳实现方式! 2025华为OD真题目录+全流程解析/备考攻略/经验分享 华为OD机试真题《最小的调整次数/特异性双端…

建筑兔零基础人工智能自学记录101|Transformer(1)-14

Transformer 谷歌提出&#xff0c;一组编码-解码器 可以同时处理&#xff0c;通过位置编码来处理单词 实质是token词语接龙&#xff08;只是有不同的概率&#xff09; token对应向量 Transformer简述 文生图就需要用到transformer黑箱 token 内部层次 中间主要是embedding…

网线水晶头接法与8根线芯作用解析

网线的正确接法至关重要&#xff0c;它直接影响网络的稳定性与传输速度。而了解每根线的作用&#xff0c;更是深入掌握网络布线知识的关键。常见的网线为非屏蔽双绞线&#xff08;UTP&#xff09;&#xff0c;内部包含 8 根不同颜色的线芯&#xff0c;两两相互缠绕&#xff0c;…

【GESP真题解析】第 2 集 GESP 三级样题卷编程题 1:逛商场

大家好,我是莫小特。 这篇文章给大家分享 GESP 三级样题卷编程题第 1 题:逛商场。 题目链接 洛谷链接:B3848 逛商场 一、完成输入 根据输入格式描述,输入一共有三行,第一行为整数 N,数据范围: 1 ≤ N ≤ 100 1 \le N \le 100 1≤N≤100,使用 int 类型。 第二行为 N …

Nacos实战——动态 IP 黑名单过滤

1、需求分析 一些恶意用户&#xff08;‏可能是黑客、爬虫、DDoS ؜攻击者&#xff09;可能频繁请求服务器资​源&#xff0c;导致资源占用过高。针对这种问题&#xff0c;可以通过IP‏ 封禁&#xff0c;可以有效拉؜黑攻击者&#xff0c;防止资源​被滥用&#xff0c;保障合法…

基于Web的濒危野生动物保护信息管理系统设计(源码+定制+开发)濒危野生动物监测与保护平台开发 面向公众参与的野生动物保护与预警信息系统

博主介绍&#xff1a; ✌我是阿龙&#xff0c;一名专注于Java技术领域的程序员&#xff0c;全网拥有10W粉丝。作为CSDN特邀作者、博客专家、新星计划导师&#xff0c;我在计算机毕业设计开发方面积累了丰富的经验。同时&#xff0c;我也是掘金、华为云、阿里云、InfoQ等平台…

流媒体协议分析:流媒体传输的基石

在流媒体传输过程中&#xff0c;协议的选择至关重要&#xff0c;它决定了数据如何封装、传输和解析&#xff0c;直接影响着视频的播放质量和用户体验。本文将深入分析几种常见的流媒体传输协议&#xff0c;探讨它们的特点、应用场景及优缺点。 协议分类概述 流媒体传输协议根据…

通过mqtt 发布温湿度

参考 用HAL库改写江科大的stm32入门例子-补充DHT11_江科大stm32安装hal库-CSDN博客 老夫上课的时候 &#xff0c;这部份讲的比较多 &#xff0c;出发点是 安利 “单总线”的具体使用。 这里无非是引入dht11 库&#xff0c; 使用前初始化 然后通话dht11库的方法 读取数据 &…

ApiHug 1.3.9 支持 Spring 3.5.0 + Plugin 0.7.4 内置小插件升级!儿童节快乐!!!

有用内置小插件 - ApiHug小插件&#xff0c;大用途https://apihug.github.io/zhCN-docs/how/005_helpful_inner_plugin SDK: [1.3.9-RELEASE] - 2025-06-01 Move the router auto-processing to an internal plugin for enhanced flexibility.Translate the OAS to json sch…