一次修改多个数据库列的格式

时间:2016-06-20 22:00:02

标签: mysql phpmyadmin format multiple-columns

我使用phpmyadmin将csv表导入sql db。我猜默认格式是十进制(8,5),或者至少是它的出现方式。似乎矫枉过正,我认为我可以减少到4,1。问题是有大约470个字段。我知道如何一次改变一个,但这需要很长时间。有更快的方法吗?

2 个答案:

答案 0 :(得分:0)

我只有Sql Server 2008 R2,但似乎MySQL解决方案可能类似。我尽可能地将它与MySQL紧密结合,但是如果没有MySQL引擎,我就无法检查它......所以它的价值在哪里,这就是我的脚本(在Sql Server中测试):

// g++ 4.8.4
int main() {
    volatile int vi;
    std::ignore = vi;

    // error: no match for ‘operator=’ (
    //     operand types are ‘const std::_Swallow_assign’
    //     and ‘std::remove_reference<volatile int&>::type {aka volatile int}’
    // )
    // std::ignore = std::move(vi);

    // However this compiles:
    volatile int&& vir = std::move(vi);
    std::ignore = vir;
}

答案 1 :(得分:0)

之前我从未使用过SqlFiddle,所以认为现在是开始的好时机,专门为MySQL 5.6提供完整的答案。请参阅http://sqlfiddle.com/#!9/19f46/1

在Build Schema面板的底部,选择Delimiter = [//]。 SqlFiddle使用它来决定何时向MySQL发送一大块代码。这是必要的,因为CREATE PROCEDURE必须作为一个块发送出去。如果使用默认的Delimiter = [; ],然后它只会将部分CREATE PROCEDURE发送到它找到的第一个;

cols选择具有您想要更改的精度和比例的decimal类型的列。当前硬盘编码为OP请求的8和5,但根据需要进行更改以仅识别要修改的列。在进行表修改以运行此选择以验证要修改的列之前,这是一个好主意。

存储过程exec_multiple使用表cols生成ALTER TABLE语句,然后动态执行。

EXECUTE一次只处理一个语句,因此您需要遍历cols行并单独应用每个ALTER TABLEid中的auto_increment列cols允许您在不使用游标的情况下依次选择每一行。

test_log捕获您在构建架构完成后可能要检查的任何调试信息。

以下内容位于左侧的Build Schema面板中。 所有逻辑都需要在此面板中,因为SqlFiddle不允许在“运行SQL”面板中使用数据定义语言或表插入/更新/删除语句。

create table if not exists cols
(
    id int auto_increment primary key
    , ownerName varchar(128)
    , tblName  varchar(128)
    , colName  varchar(128)
    , colType  varchar(128)
    , colPrecision int
    , colScale int
) //

create table if not exists test_table
(
    testDecimal1 decimal(8,5)
    , testDecimal2 decimal(8,5)
) //

create table if not exists test_table2
(
    testDecimal3 decimal(8,5)
    , testDecimal4 decimal(8,5)
) //

create table if not exists test_log
(
    msg varchar(1024)
) //

INSERT INTO cols
( ownerName, tblName, colName, colType, colPrecision, colScale )
SELECT TABLE_SCHEMA, `TABLE_NAME`, COLUMN_NAME, DATA_TYPE, NUMERIC_PRECISION, NUMERIC_SCALE
FROM INFORMATION_SCHEMA.COLUMNS
WHERE DATA_TYPE = 'decimal' AND NUMERIC_PRECISION = 8 AND NUMERIC_SCALE = 5 //

insert test_log( msg) select database() //

CREATE PROCEDURE `exec_multiple` ( newPrecision int, newScale int)
BEGIN
    declare n int; 
    declare nrows int;
    declare sql_stmt varchar(1024);
    set n = 1;
    select count(*) from cols into nrows;

    while n <= nrows do

        select CONCAT('ALTER TABLE '
        , ownerName, '.', tblName, ' MODIFY COLUMN '
        , colName, ' decimal(', newPrecision, ','
        , newScale, ')') into sql_stmt from `cols` where id = n;

        SET @sql_stmt := sql_stmt;  -- not sure why this is necessary

        insert test_log( msg ) select @sql_stmt;

        PREPARE dynamic_statement FROM @sql_stmt;
        EXECUTE dynamic_statement;
        DEALLOCATE PREPARE dynamic_statement;

        set n = n + 1;
    end while;
END //

call exec_multiple(4, 1) //

这在右侧的“运行SQL”面板中进行了

select * from test_log;

SELECT TABLE_SCHEMA, `TABLE_NAME`, COLUMN_NAME, DATA_TYPE, NUMERIC_PRECISION, NUMERIC_SCALE
FROM INFORMATION_SCHEMA.COLUMNS
WHERE DATA_TYPE = 'decimal'
;

select * from cols;