Skip to content

OPEN SQL 读取数据

一、 数据查询 (SELECT)

1.查询sql语法:

abap
SELECT [SINGLE] <字段列表> 
FROM <表名> 
[INTO|APPENDING <目标结构>] 
[WHERE <条件>] 
[GROUP BY <分组字段>] 
[HAVING <分组条件>] 
[ORDER BY <排序字段>]. 
ENDSELECT.   " 仅用于逐行读取模式‌
  • 单行查询‌SELECT SINGLE 用于精确匹配单条记录,需配合唯一条件使用‌; 示例:SELECT SINGLE name INTO @DATA(lv_name) FROM zuser WHERE id = '001'‌
  • 动态查询‌:支持运行时指定字段列表‌8 示例:SELECT (lv_fields) FROM ztable INTO TABLE @DATA(lt_data)‌
  • 结果处理‌INTO TABLE 直接填充内表 APPENDING 追加数据到现有内表‌3

2.去重查询 DISTINCT

abap
SELECT DISTINCT carrid FROM sflight INTO TABLE @DATA(lt_airlines)‌
  • 自动过滤重复记录,常用于枚举值查询‌
  • ‌注意‌:大数据量使用可能导致性能问题‌

二、数据检索变式

1.单行查询

abap
SELECT SINGLE <字段> 
FROM <表名> 
INTO @DATA(ls_data) 
WHERE <唯一条件>.
  • 必须指定唯一条件字段(主键优先)‌

2. 动态字段选择

abap
DATA(lv_fields) = 'CARRID, CONNID'.
SELECT (lv_fields) 
FROM sflight 
INTO TABLE @DATA(lt_dyn).
  • 支持运行时动态指定字段列表‌

3.联合查询

abap
SELECT a~carrid, b~connid 
FROM spfli AS a 
INNER JOIN sflight AS b 
ON a~carrid = b~carrid 
INTO TABLE @DATA(lt_join).
  • 支持INNER JOIN/LEFT OUTER JOIN

INNER JOIN

  • 定义‌:仅返回两个表中‌完全匹配‌的记录,未匹配数据自动过滤
  • ABAP 语法‌:
    abap
    SELECT a~carrid, b~connid 
    FROM spfli AS a 
    INNER JOIN sflight AS b 
    ON a~carrid = b~carrid 
    INTO TABLE @DATA(lt_data)‌

‌LEFT OUTER JOIN‌

  • ‌定义‌‌:返回左表‌全部记录‌ + 右表匹配记录(无匹配时右表字段为 NULL)‌47
  • ‌典型场景‌‌:需包含主表全部数据(如订单主表+详情表关联)‌4

‌RIGHT OUTER JOIN‌

  • ‌‌定义‌‌‌:返回右表‌全部记录‌ + 左表匹配记录(使用频率较低)‌

4.内标筛查(FOR ALL ENTRIES)

FOR ALLENTRY语句与嵌套SELECT语句或Subquery的功能相似。使用FOR ALL ENTRY语句时,WHERE语句中使用的条件必须是itab中存在的字段。

abap
DATA(lt_filter) = VALUE RANGE(...).  
SELECT * FROM sflight 
  INTO TABLE @DATA(lt_filtered) 
  FOR ALL ENTRIES IN @lt_filter 
  WHERE carrid = @lt_filter-carrid‌

注意‌:

  • itab的字段要与比较对象的表字段类型一致。
  • 不能使用类似LIKE、BETWEEN、IN等比较语句itab 中自动删除重复数据(Unique Key为基准)。
  • itab为空则取得所有数据。
  • itab 中数据多时会增加LOOP 循环次数,因此会降低选择速度。例如 itab 中数据为 3 条,则会执行3次“SELECT~ENDSELECT”。

[‌案例‌]是先查询存储航班时刻表的数据库表spfi 的所有数据后用FOR ALLENTRIES语句从日期别航班运行信息数据库表中查询相关数据的程序。

abap
REPORT z03 10.
DATA gt spfli TYPE TABLE OF spfli.
DATA gt sflight TYPE TABLE OF sflight.
DATA gs sflight TYPE sflight.

SELECT * FROM spfli
INTO TABLE gt spfli.

SELECT * FROM sflight
    INTO TABLE gt sflight
    FOR ALL ENTRIES IN gt spfli
    WHERE carrid =gt spfli-carrid
    AND connid = gt spfli-connid.

LOOP AT gt sflight INTo gs sflight.
    WRITE : /gs sflight-carrid, gs sflight-connid.
ENDLOOP.

三、WHERE 子句条件类型

条件类型语法示例适用场景
精确匹配WHERE carrid = 'LH'主键/索引字段查询
范围查询WHERE fldate BETWEEN '20250101' AND '20251231'日期/数值区间筛选
模糊查询WHERE cityfrom LIKE 'Frank%'部分字符串匹配场景
集合筛选WHERE carrid IN ('LH','AA','DL')多值筛选场景
动态条件WHERE (lv_where_cond)
(lv_where_cond = carrid = 'LH')
运行时条件动态生成

关键特性说明

  1. 精确匹配‌:通过等号直接定位特定值,适用于主键或二级索引字段的高效检索;
  2. 范围查询‌:使用BETWEEN运算符快速筛选连续区间数据(如时间范围、金额区间)‌;
  3. 模糊查询‌:利用LIKE配合通配符%_进行模式匹配,常用于模糊搜索场景;
  4. 集合筛选‌:通过IN运算符批量匹配多个离散值,优化多值查询性能;
  5. 动态条件‌:支持运行时拼接条件字符串,实现灵活的条件组合逻辑。

四、高级功能

1. 分组统计

abap
SELECT carrid, SUM( price ) AS total 
FROM sflight 
GROUP BY carrid 
HAVING total > 10000 
INTO TABLE @DATA(lt_sum).
  • GROUP BY与聚合函数配合使用‌
  • HAVING过滤分组结果‌
聚合函数与分组统计一起使用
函数描述示例备注
COUNT(*)统计查询结果记录总数COUNT(*) AS cnt包含NULL值记录统计
SUM()数值型字段求和SUM( price ) AS total仅对数值字段有效
AVG()计算数值字段平均值AVG( price ) AS avg_price自动排除NULL值计算
MAX()获取字段最大值MAX( fldate ) AS last_date支持日期/数值/字符型

使用示例

abap
" 航班数据统计查询
SELECT carrid,
       COUNT(*)  AS flight_count,
       SUM( seatsocc ) AS occupied_total,
       AVG( price )    AS average_price,
       MAX( fldate )   AS last_flight_date
  FROM sflight
  INTO TABLE @DATA(lt_stats)
  GROUP BY carrid.  -- 必须使用GROUP BY分组‌
使用注意:
  • 1.NULL值处理‌:AVG()函数自动忽略NULL值,COUNT(*)包含所有记录‌
  • 2.‌数据类型匹配‌:SUM()/AVG()仅适用数值字段,MAX()支持排序字段‌
  • 3.分组要求‌:使用聚合函数时必须搭配GROUP BY子句(COUNT(*)除外)‌

2. 子查询应用

abap
SELECT * FROM sflight 
WHERE carrid IN ( 
  SELECT carrid FROM spfli 
  WHERE countryto = 'CN' 
).
  • 支持IN、EXISTS等子查询类型‌

3.结果排序 (ORDER BY)

abap
SELECT * FROM sflight 
  INTO TABLE @DATA(lt_sorted) 
  ORDER BY fldate DESCENDING, carrid ASCENDING

4. 游标分页

abap
DATA: lv_cursor TYPE cursor.
OPEN CURSOR lv_cursor FOR 
SELECT * FROM sflight WHERE carrid = 'LH'.
FETCH NEXT CURSOR lv_cursor 
INTO TABLE @DATA(lt_page) PACKAGE SIZE 100.
  • 适用于大数据量分批次处理‌

五、性能优化要点

  • 行数限制‌UP TO 100 ROWS 限制返回行数‌
  • 字段精简‌:避免SELECT *,明确指定必要字段‌
  • 索引匹配‌:WHERE条件优先使用索引字段‌
  • 批量操作‌:减少循环中执行SELECT次数‌

六、综合应用示例

abap
" 分页查询+动态字段+分组统计
DATA: lv_fields TYPE string VALUE 'CARRID, AVG( PRICE ) AS avg_price',
      lv_offset TYPE i VALUE 0.

DO 3 TIMES.
  SELECT (lv_fields)
  FROM sflight
  GROUP BY carrid
  ORDER BY avg_price DESC
  INTO TABLE @DATA(lt_report)
  UP TO 50 ROWS
  OFFSET @lv_offset.
  
  lv_offset = lv_offset + 50.
ENDDO.