Flink RowData 与 Row 相互转化工具类

RowData与Row区别

(0)都代表了一条记录。都可以设置RowKind,和列数量Aritry。

(1)RowData 属于Table API,而Row属于Stream API

(2)RowData 属于Table内部接口,对用户不友好。而Row使用简单。

(3)RowData 要拿到field值必须提供列索引和LogicalType类型。而Row只需要提供列名或列索引即可。

请自己阅读注释内容。

java 复制代码
import org.apache.flink.api.common.functions.MapFunction;
import org.apache.flink.api.common.typeinfo.TypeInformation;
import org.apache.flink.api.java.typeutils.ResultTypeQueryable;
import org.apache.flink.api.java.typeutils.RowTypeInfo;
import org.apache.flink.table.data.GenericRowData;
import org.apache.flink.table.data.RowData;
import org.apache.flink.table.runtime.typeutils.InternalTypeInfo;
import org.apache.flink.table.types.DataType;
import org.apache.flink.table.types.logical.LogicalType;
import org.apache.flink.table.types.logical.LogicalTypeRoot;
import org.apache.flink.table.types.logical.RowType;
import org.apache.flink.types.Row;
import org.apache.flink.util.Preconditions;


import java.util.*;
import java.util.stream.Collectors;

/**
 * @author: lisai
 * @create: 2023-03-15 16:51
 * @Description:
 */
public class RowUtils {

    public interface TypedMapFunc<IN, OUT> extends MapFunction<IN, OUT>, ResultTypeQueryable<OUT> {
        DataType getProducedDataType();
    }

    public static List<RowData.FieldGetter> getRowDataFieldGetters(DataType rowDataType) {
        Preconditions.checkArgument(rowDataType.getLogicalType().getTypeRoot() == LogicalTypeRoot.ROW);
        return getRowDataFieldGetters(rowDataType.getChildren().stream().map(DataType::getLogicalType).collect(Collectors.toList()));
    }

    public static List<RowData.FieldGetter> getRowDataFieldGetters(RowType rowType) {
        return getRowDataFieldGetters(rowType.getFields().stream().map(RowType.RowField::getType).collect(Collectors.toList()));
    }

    public static List<RowData.FieldGetter> getRowDataFieldGetters(List<LogicalType> logicalTypes) {
        List<RowData.FieldGetter> fieldGetterList = new ArrayList<>();
        for (int i = 0; i < logicalTypes.size(); i++) {
            final RowData.FieldGetter fieldGetter = RowData.createFieldGetter(logicalTypes.get(i), i);
            fieldGetterList.add(fieldGetter);
        }
        return fieldGetterList;
    }

    public static void copyRowData(RowData input, GenericRowData output, List<RowData.FieldGetter> fieldGetters) {
        for (int i = 0; i < input.getArity() && i < output.getArity(); i++) {
            if (input instanceof GenericRowData) {
                output.setField(i, ((GenericRowData) input).getField(i));
            } else {
                Preconditions.checkArgument(fieldGetters != null);
                Object value = fieldGetters.get(i).getFieldOrNull(input);
                output.setField(i, value);
            }
        }
    }

    public static TypedMapFunc<RowData, Row> getRowDataToRowMapFunc(DataType rowDataType) {
        LogicalType logicalType = rowDataType.getLogicalType();
        Preconditions.checkArgument(logicalType.getTypeRoot() == LogicalTypeRoot.ROW);
        return new TypedMapFunc<RowData, Row>() {
            private RowData.FieldGetter[] fieldGetters = getRowDataFieldGetters(rowDataType).toArray(new RowData.FieldGetter[0]);
            @Override
            public TypeInformation<Row> getProducedType() {
                RowType rowType = (RowType) logicalType;
                List<RowType.RowField> rowFields = rowType.getFields();
                List<DataType> rowDataTypes = rowDataType.getChildren();
                TypeInformation<?>[] fieldTypeInfos = rowDataTypes.stream().map(t -> InternalTypeInfo.of(t.getLogicalType())).toArray(TypeInformation[]::new);
                String[] fieldNames = rowFields.stream().map(RowType.RowField::getName).toArray(String[]::new);
                return new RowTypeInfo(fieldTypeInfos, fieldNames);
            }

            @Override
            public DataType getProducedDataType() {
                return rowDataType.bridgedTo(Row.class);
            }

            @Override
            public Row map(RowData rowData) throws Exception {
                Row row = new Row(rowData.getRowKind(), rowData.getArity());
                for (int i = 0; i < rowData.getArity(); i++) {
                    RowData.FieldGetter fieldGetter = fieldGetters[i];
                    row.setField(i, fieldGetter.getFieldOrNull(rowData));
                }
                return row;
            }
        };
    }

    public static TypedMapFunc<Row, RowData> getRowToRowRowMapFunc(DataType rowDataType) {
        Preconditions.checkArgument(rowDataType.getLogicalType().getTypeRoot() == LogicalTypeRoot.ROW);
        return new TypedMapFunc<Row, RowData>() {
            /**
             * @Description: 注意input Row中所有的数据类型必须是Flink Table API规定的内部类型。具体参考 {@DataTypeUtils.toInternalDataType()}
             * @param
             * @return TypeInformation<org.apache.flink.table.data.RowData>
             */
            @Override
            public TypeInformation<RowData> getProducedType() {
                return InternalTypeInfo.of((RowType)rowDataType.getLogicalType());
            }

            @Override
            public DataType getProducedDataType() {
                return rowDataType.bridgedTo(RowData.class);
            }

            @Override
            public RowData map(Row row) throws Exception {
                GenericRowData rowData = new GenericRowData(row.getKind(), row.getArity());
                for (int i = 0; i < rowData.getArity(); i++) {
                    rowData.setField(i, row.getField(i));
                }
                return rowData;
            }
        };
    }

}
相关推荐
2401_8830410835 分钟前
新锐品牌电商代运营公司都有哪些?
大数据·人工智能
青云交38 分钟前
大数据新视界 -- 大数据大厂之 Impala 性能优化:融合机器学习的未来之路(上 (2-1))(11/30)
大数据·计算资源·应用案例·数据交互·impala 性能优化·机器学习融合·行业拓展
Json_181790144803 小时前
An In-depth Look into the 1688 Product Details Data API Interface
大数据·json
Qspace丨轻空间6 小时前
气膜场馆:推动体育文化旅游创新发展的关键力量—轻空间
大数据·人工智能·安全·生活·娱乐
Elastic 中国社区官方博客7 小时前
如何将数据从 AWS S3 导入到 Elastic Cloud - 第 3 部分:Elastic S3 连接器
大数据·elasticsearch·搜索引擎·云计算·全文检索·可用性测试·aws
Aloudata8 小时前
从Apache Atlas到Aloudata BIG,数据血缘解析有何改变?
大数据·apache·数据血缘·主动元数据·数据链路
水豚AI课代表8 小时前
分析报告、调研报告、工作方案等的提示词
大数据·人工智能·学习·chatgpt·aigc
拓端研究室TRL11 小时前
【梯度提升专题】XGBoost、Adaboost、CatBoost预测合集:抗乳腺癌药物优化、信贷风控、比特币应用|附数据代码...
大数据
黄焖鸡能干四碗11 小时前
信息化运维方案,实施方案,开发方案,信息中心安全运维资料(软件资料word)
大数据·人工智能·软件需求·设计规范·规格说明书
编码小袁11 小时前
探索数据科学与大数据技术专业本科生的广阔就业前景
大数据