ABAP定义Range

**

ABAP定义Range

**

Range使用
Range Table为SAP R/3系统标准内表的一种,结构与Selection Table一致,由SIGN,OPTION,LOW,HIGH字段组成。Range Table 常用于 Open SQL 语句中的条件筛选,变式判断,可以优化取数效率与程序性能.

当然要注意 RANGE 的行项目有上限的,在 ECC6 中大概 2 万行将导致 ABAP DUMP。
定义
DATA: range_tab {TYPE RANGE OF type} | {LIKE RANGE OF dobj}.

DATA: gr_werks TYPE RANGE OF werks_d WITH HEADER LINE, gw_werks LIKE LINE OF gr_werks.

RANGES range_tab FOR dobj [OCCURS n] :创建一个选择表

For 后面字段必须为参考表的字段,不能使用 Data Element 来定义.
使用
RANGES: gr_matnr FOR marc-matnr.
gr_matnr-sign = ‘I’
gr_matnr-option = ‘EQ’
gr_matnr-low = xxx
gr_matnr-high = xxx
APPEND gr_matnr.
内表gr_matnr按照选择表结构创建,字段参照数据库表字段。
在这里插入图片描述

选择表
系统为每个 SELECT-OPTIONS 语句创建选择表。选择表的目的是按标准化的方式保存复合选择限制。它们可按多种方式使用。它们的主要目的是使用 Open SQL 语句的 WHERE 子句 把选择标准直接传输到数据库表。

选择表是一个带表头行的内表。它的行结构是字段字符串,由四个组件构成,即 SIGN、OPTION、LOW 和 HIGH。每个选择表行表示数据选择的条件:

SIGN:控制保存在OPTION中的运算符是否需要翻转。
I:包含标准-运算符不翻转
E:排除标准-运算符翻转
OPTION:包含选择运算符
HIGH为空:可以使用EQ、NE、GT、LE、LT、CP、NP运算符
HIGH不空:可以使用BT、NB运算符
LOW:LOW的数据类型与参照的标准表字段一致
HIGH为空:LOW的内容定义单值选择,与OPTION结合指定条件
HIGH不空:LOW与HIGH共同组成范围值
HIGH:为间隔选择指定上界
将选择表转换为 Range
在这里插入图片描述

<think>我们讨论的是ABAP中的RANGE表。RANGE表在ABAP中常用于构建条件范围,特别是在数据库查询的WHERE条件中,可以表示一个字段的多个区间条件(如BETWEEN, IN等)。RANGE表实际上是一个标准内表,其行结构包含以下几个字段: SIGN: 类型为CHAR1,取值为'I'(包含)或'E'(排除) OPTION: 类型为CHAR2,表示操作符,如'EQ'(等于)、'BT'(介于之间)、'NE'(不等于)等 LOW: 范围的下限 HIGH: 范围的上限(当使用BT、NB等操作符时需要) 下面我们将详细介绍如何定义、填充和使用RANGE表。 步骤1:定义RANGE表 有两种方式定义RANGE表: a) 使用标准类型RANGE OF,但需要先定义元素类型 b) 直接使用TYPE RANGE OF后面跟字段类型(如TYPE RANGE OF matnr) 步骤2:填充RANGE表 可以使用VALUE #(...)直接构造,也可以逐行APPEND。 步骤3:在ABAP语句中使用(如SELECT、LOOP等) 示例代码:</think>### ABAP `RANGE` 表详解:高效数据筛选利器 在 ABAP 中,`RANGE` 表是用于**动态条件筛选**的核心数据结构,特别适用于数据库查询、内表筛选等场景。它本质上是包含 `SIGN`、`OPTION`、`LOW`、`HIGH` 字段的标准内表。 --- ### 1. RANGE 表结构解析 | 字段名 | 类型 | 长度 | 说明 | |--------|------|------|------| | SIGN | C | 1 | 包含/排除标志:`I`(包含), `E`(排除) | | OPTION | C | 2 | 比较运算符:`EQ`(等于), `BT`(介于), `NE`(不等于)等 | | LOW | 任意 | - | 范围下限值 | | HIGH | 任意 | - | 范围上限值(仅用于 `BT`/`NB`) | --- ### 2. 创建 RANGE 表的三种方式 #### 方式1:直接类型声明 ```abap " 定义物料号范围表 DATA: gt_matnr_range TYPE RANGE OF matnr. ``` #### 方式2:基于结构体定义 ```abap TYPES: BEGIN OF ty_custom_range, sign TYPE ddsign, option TYPE ddoption, low TYPE kunnr, high TYPE kunnr, END OF ty_custom_range. DATA: gt_customer_range TYPE TABLE OF ty_custom_range. ``` #### 方式3:使用 RTTS 动态创建 ```abap DATA: lo_type TYPE REF TO cl_abap_datadescr, lt_range TYPE REF TO data. lo_type = cl_abap_datadescr=>describe_by_name( 'BUKRS' ). " 公司代码类型 CREATE DATA lt_range TYPE RANGE OF (lo_type->absolute_name). ASSIGN lt_range->* TO FIELD-SYMBOL(<fs_range>). ``` --- ### 3. RANGE 表填充方法 #### 方法1:VALUE 操作符(推荐) ```abap gt_matnr_range = VALUE #( ( sign = 'I' option = 'EQ' low = 'MAT001' ) " 包含 MAT001 ( sign = 'I' option = 'BT' low = 'MAT100' high = 'MAT200' ) " 包含 MAT100-MAT200 ( sign = 'E' option = 'EQ' low = 'MAT999' ) " 排除 MAT999 ). ``` #### 方法2:APPEND 语句 ```abap APPEND VALUE #( sign = 'I' option = 'GE' low = '20240101' ) TO gt_date_range. ``` #### 方法3:函数生成 ```abap CALL FUNCTION 'F4IF_FIELD_VALUE_REQUEST' EXPORTING fieldname = 'KUNNR' TABLES return_tab = gt_customer_range. ``` --- ### 4. 实际应用场景 #### 场景1:数据库查询 ```abap SELECT * FROM vbak INTO TABLE @DATA(gt_orders) WHERE vbeln IN @gt_vbeln_range " 销售单据范围 AND erdat IN @gt_date_range. " 日期范围 ``` #### 场景2:内表筛选 ```abap DATA(gt_filtered_data) = FILTER #( gt_source_data USING KEY primary_key WHERE werks IN gt_plant_range AND matkl IN gt_matkl_range ). ``` #### 场景3:ALV 筛选器 ```abap DATA: go_alv TYPE REF TO cl_salv_table. go_alv->get_filters( )->add_filter( columnname = 'LIFNR' sign = 'I' option = 'BT' low = 'V0001' high = 'V9999' ). ``` --- ### 5. 高级操作技巧 #### 技巧1:范围合并 ```abap APPEND LINES OF gt_range1 TO gt_combined_range. APPEND LINES OF gt_range2 TO gt_combined_range. SORT gt_combined_range BY low high. DELETE ADJACENT DUPLICATES FROM gt_combined_range. ``` #### 技巧2:范围反转 ```abap LOOP AT gt_range ASSIGNING FIELD-SYMBOL(<range>). <range>-sign = COND #( WHEN <range>-sign = 'I' THEN 'E' ELSE 'I' ). ENDLOOP. ``` #### 技巧3:动态范围生成 ```abap DATA: lv_sql_cond TYPE string. LOOP AT gt_range ASSIGNING FIELD-SYMBOL(<r>). DATA(lv_cond) = |{ <r>-low }| && COND #( WHEN <r>-option = 'BT' THEN | AND { <r>-high }| ELSE '' ). lv_sql_cond = |{ lv_sql_cond } OR (FIELD { <r>-sign } { <r>-option } { lv_cond })|. ENDLOOP. " 生成动态 WHERE 条件 SELECT * FROM mara WHERE (lv_sql_cond). ``` --- ### 6. 性能优化指南 1. **索引优化**: ```abap " 确保范围表按 LOW 字段排序 SORT gt_range BY low. ``` 2. **范围合并**: ```abap " 合并连续范围 LOOP AT gt_range ASSIGNING <curr>. AT END OF low. <curr>-high = <curr>-low. " 单值范围优化 ENDAT. ENDLOOP. ``` 3. **避免大范围**: ```abap " 限制范围大小 IF lines( gt_range ) > 1000. " 分批次处理 ENDIF. ``` 4. **使用 BINARY SEARCH**: ```abap READ TABLE gt_range WITH KEY low = lv_value BINARY SEARCH TRANSPORTING NO FIELDS. ``` --- ### 7. 实际应用案例:物料状态筛选器 ```abap DATA: gt_mat_status TYPE RANGE OF msta. " 构建状态范围 gt_mat_status = VALUE #( ( sign = 'I' option = 'EQ' low = 'A' ) " 激活 ( sign = 'I' option = 'EQ' low = 'B' ) " 冻结 ( sign = 'E' option = 'EQ' low = 'X' ) " 删除 ). " 应用筛选 SELECT matnr, maktx FROM mara INTO TABLE @DATA(gt_materials) WHERE mstae IN @gt_mat_status AND matnr IN @gt_matnr_range. " 显示结果 cl_demo_output=>display( gt_materials ). ``` --- ### 常见错误处理 1. **类型不匹配**: ```abap TRY. gt_range = VALUE #( ( sign = 'I' option = 'EQ' low = lv_value ) ). CATCH cx_sy_conversion_error. " 处理类型转换错误 ENDTRY. ``` 2. **空范围处理**: ```abap IF gt_range IS INITIAL. " 处理空范围情况 ELSE. " 正常处理 ENDIF. ``` 3. **无效选项**: ```abap IF <range>-option NOT IN ('EQ','NE','GT','LT','GE','LE','BT','NB'). " 抛出异常 ENDIF. ``` ---
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

SAP 的寒

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值