124

制限を変更するにはどうすればよいですか

行サイズが大きすぎます (> 8126)。一部の列を TEXT または BLOB に変更するか、使用ROW_FORMAT=DYNAMIC or ROW_FORMAT=COMPRESSEDすると役立つ場合があります。現在の行形式でBLOBは、768 バイトのプレフィックスがインラインで格納されます。

テーブル:

id  int(11) No       
name    text    No       
date    date    No       
time    time    No       
schedule    int(11) No       
category    int(11) No       
top_a   varchar(255)    No       
top_b   varchar(255)    No       
top_c   varchar(255)    No       
top_d   varchar(255)    No       
top_e   varchar(255)    No       
top_f   varchar(255)    No       
top_g   varchar(255)    No       
top_h   varchar(255)    No       
top_i   varchar(255)    No       
top_j   varchar(255)    No       
top_title_a varchar(255)    No       
top_title_b varchar(255)    No       
top_title_c varchar(255)    No       
top_title_d varchar(255)    No       
top_title_e varchar(255)    No       
top_title_f varchar(255)    No       
top_title_g varchar(255)    No       
top_title_h varchar(255)    No       
top_title_i varchar(255)    No       
top_title_j varchar(255)    No       
top_desc_a  text    No       
top_desc_b  text    No       
top_desc_c  text    No       
top_desc_d  text    No       
top_desc_e  text    No       
top_desc_f  text    No       
top_desc_g  text    No       
top_desc_h  text    No       
top_desc_i  text    No       
top_desc_j  text    No       
status  int(11) No       
admin_id    int(11) No 
4

18 に答える 18

130

serverfaultでも質問されました。

MySQL の行サイズについて詳しく説明しているこの記事をご覧になることをお勧めします。TEXT または BLOB フィールドを使用する場合でも、各フィールドの最初の 768 バイトがインラインでページに格納されるため、行サイズが 8K (InnoDB の制限) を超える可能性があることに注意することが重要です。

これを修正する最も簡単な方法は 、InnoDB でBarracuda ファイル形式を使用することです。これは基本的に、最初の 768 バイトを格納する代わりに、テキスト データへの 20 バイト ポインタのみを格納することで、問題を完全に取り除きます。


OPで機能した方法は次のとおりです。

  1. my.cnfセクションの下のファイルに次を追加します[mysqld]

    innodb_file_per_table=1
    innodb_file_format = Barracuda
    
  2. ALTER使用するテーブルROW_FORMAT=COMPRESSED

    ALTER TABLE nombre_tabla
        ENGINE=InnoDB
        ROW_FORMAT=COMPRESSED 
        KEY_BLOCK_SIZE=8;
    

上記の方法でも問題が解決しない可能性があります。これは、 InnoDBエンジンの既知の (および検証済みの) バグであり、現時点での一時的な修正は、一時ストレージとしてMyISAMエンジンにフォールバックすることです。だから、あなたのファイルで:my.cnf

internal_tmp_disk_storage_engine=MyISAM
于 2013-03-23T10:32:24.967 に答える
2

Laravel Homestead (Vagrant) ボックスを破棄して新たに開始すると、この問題が発生し続けます。

  1. コマンド ラインからボックスに SSH 接続するhomestead ssh

  2. my.cnf ファイルに移動しますsudo vi /etc/mysql/my.cnf

  3. 以下の行をファイルの最後 (!includedir の下) に追加します。

    [mysqld]

    innodb_log_file_size=512M

    innodb_strict_mode=0

  4. 変更を my.cnf に保存してから、MYSQL をリロードします。sudo service mysql restart

于 2020-12-03T03:04:35.033 に答える
0

私も同じ問題に遭遇しました。次のSQLを実行して問題を解決します。

ALTER ${table} ROW_FORMAT=COMPRESSED;

しかし、 Row Storageについて知っておくべきだと思います。列には、可変長列(VARCHAR、VARBINARY、BLOB および TEXT 型など) と固定長列
の 2 種類があります。それらはさまざまなタイプのページに保存されます。

可変長列は、この規則の例外です。長すぎて B ツリー ページに収まらない BLOB や VARCHAR などの列は、オーバーフロー ページと呼ばれる個別に割り当てられたディスク ページに格納されます。このような列をページ外列と呼びます。これらの列の値は、オーバーフロー ページの単一リンク リストに格納され、各列には、1 つ以上のオーバーフロー ページの独自のリストがあります。場合によっては、長い列の値のすべてまたはプレフィックスが B ツリーに格納され、ストレージの浪費を回避し、別のページを読み取る必要がなくなります。

ROW_FORMAT を設定する目的が

テーブルが ROW_FORMAT=DYNAMIC または ROW_FORMAT=COMPRESSED で作成された場合、InnoDB は長い可変長カラム値 (VARCHAR、VARBINARY、BLOB および TEXT タイプの場合) を完全にオフページに格納でき、クラスター化されたインデックス レコードには 20 のみが含まれます。オーバーフロー ページへのバイト ポインタ。

DYNAMIC および COMPRESSED 行フォーマットについて詳しく知りたい

于 2017-06-14T09:01:05.517 に答える
0

これが多くの列を持つ SELECT で発生する場合、mysql が一時テーブルを作成していることが原因である可能性があります。このテーブルが大きすぎてメモリに収まらない場合、デフォルトの一時テーブル形式である InnoDB を使用してディスクに格納します。この場合、InnoDB のサイズ制限が適用されます。

次に、4 つのオプションがあります。

  1. サーバーの再初期化が必要な別の投稿に記載されているように、innodb行サイズ制限を変更します。
  2. クエリを変更して含まれる列を少なくするか、一時テーブルを作成しないようにします (つまり、order by 句と limit 句を削除します)。
  3. max_heap_table_sizeを大きく変更して、結果がメモリに収まるようにし、ディスクに書き込む必要がないようにします。
  4. デフォルトの一時テーブル形式を MYISAM に変更します。これが私が行ったことです。my.cnf の変更:

    internal_tmp_disk_storage_engine=MYISAM
    

mysql を再起動すると、クエリが機能します。

于 2019-07-10T08:39:04.053 に答える