Cant get rid of filesort in simple queryHigh Disk IO, How to mitigate?EXPLAIN output suggests that my index...

How can I differentiate duration vs starting time

Draw triangle with text in vertices/edges

Cryptic cross... with words

Boss asked me to sign a resignation paper without a date on it along with my new contract

What is the smallest molar volume?

Found a major flaw in paper from home university – to which I would like to return

How do I avoid the "chosen hero" feeling?

Why and/or operations in python statement are behaving unexpectedly?

How do I add a strong "onion flavor" to the biryani (in restaurant style)?

Now...where was I?

How bad is a Computer Science course that doesn't teach Design Patterns?

Reduce Reflections

Why don't you get burned by the wood benches in a sauna?

Is there any danger of my neighbor having my wife's signature?

Can I do anything else with aspersions other than cast them?

Can a Hydra make multiple opportunity attacks at once?

Identical projects by students at two different colleges: still plagiarism?

How to transport 10,000 terrestrial trolls across ocean fast?

Why is Shelob considered evil?

What are some good alternatives to Whisper for blockchain messaging?

What's the meaning of #0?

Spells that would be effective against a Modern Day army but would NOT destroy a fantasy one

Exploding Numbers

Checking if an integer permutation is cyclic in Java



Cant get rid of filesort in simple query


High Disk IO, How to mitigate?EXPLAIN output suggests that my index is not being usedFilesort while using primary key for orderbyIdentical query, tables, but different EXPLAIN and performanceWhy does IN (subquery) perform bad when = (subquery) is blazing fast?Deciding which MySQL execution plan is betterOptimizing slow queryOptimizing a simple query on a large tableselect MAX() from MySQL view (2x INNER JOIN) is slowPerformance of mysql equi-join observed in HDD and SSD













2















I have two tables. One for texts and one to assign those texts to categories. I want to select texts of one specific category and order them by last change date. So, I am using this query:



SELECT 
t2.text_id
FROM
texts_to_categories AS t1,
texts AS t2
WHERE
t1.category_id = 123
AND t2.text_id = t1.text_id
ORDER BY
t2.time_changed DESC
LIMIT 10


I tried a lot of index combinations but I keep getting a temporary and filesort:



id  select_type table   type    possible_keys                   key         key_len ref         rows    extra
1 SIMPLE t1 ref text_id,text_id_2,category_id category_id 5 const 203 Using where; Using temporary; Using filesort
1 SIMPLE t2 eq_ref PRIMARY,text_id PRIMARY 4 text_id 1 Using where


Edit: Here is a CREATE TABLE for the two tables:



CREATE TABLE `texts` (
`text_id` int(11) unsigned NOT NULL AUTO_INCREMENT,
`time_changed` datetime DEFAULT NULL,
PRIMARY KEY (`text_id`),
KEY `time_changed` (`time_changed`)
) ENGINE=InnoDB AUTO_INCREMENT=132207 DEFAULT CHARSET=utf8

CREATE TABLE `texts_to_categories` (
`id` int(11) unsigned NOT NULL AUTO_INCREMENT,
`text_id` int(11) DEFAULT NULL,
`category_id` int(11) DEFAULT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `text_id` (`text_id`,`category_id`),
KEY `text_id_2` (`text_id`),
KEY `category_id` (`category_id`)
) ENGINE=InnoDB AUTO_INCREMENT=740789 DEFAULT CHARSET=utf8









share|improve this question
















bumped to the homepage by Community 6 mins ago


This question has answers that may be good or bad; the system has marked it active so that they can be reviewed.
















  • Can you add show create table ... for the two tables? The query plan doesn't seem to use any index.

    – Giovanni
    Mar 10 '15 at 13:40











  • Okay, I edited my post.

    – leoj
    Mar 11 '15 at 2:16











  • An index on (category_id, text_id) would help your query more than the ones you have. It would also be good if you provided the whole EXPLAIN output (and not cut some parts off) so we can see which indexes are used.

    – ypercubeᵀᴹ
    Mar 11 '15 at 9:00
















2















I have two tables. One for texts and one to assign those texts to categories. I want to select texts of one specific category and order them by last change date. So, I am using this query:



SELECT 
t2.text_id
FROM
texts_to_categories AS t1,
texts AS t2
WHERE
t1.category_id = 123
AND t2.text_id = t1.text_id
ORDER BY
t2.time_changed DESC
LIMIT 10


I tried a lot of index combinations but I keep getting a temporary and filesort:



id  select_type table   type    possible_keys                   key         key_len ref         rows    extra
1 SIMPLE t1 ref text_id,text_id_2,category_id category_id 5 const 203 Using where; Using temporary; Using filesort
1 SIMPLE t2 eq_ref PRIMARY,text_id PRIMARY 4 text_id 1 Using where


Edit: Here is a CREATE TABLE for the two tables:



CREATE TABLE `texts` (
`text_id` int(11) unsigned NOT NULL AUTO_INCREMENT,
`time_changed` datetime DEFAULT NULL,
PRIMARY KEY (`text_id`),
KEY `time_changed` (`time_changed`)
) ENGINE=InnoDB AUTO_INCREMENT=132207 DEFAULT CHARSET=utf8

CREATE TABLE `texts_to_categories` (
`id` int(11) unsigned NOT NULL AUTO_INCREMENT,
`text_id` int(11) DEFAULT NULL,
`category_id` int(11) DEFAULT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `text_id` (`text_id`,`category_id`),
KEY `text_id_2` (`text_id`),
KEY `category_id` (`category_id`)
) ENGINE=InnoDB AUTO_INCREMENT=740789 DEFAULT CHARSET=utf8









share|improve this question
















bumped to the homepage by Community 6 mins ago


This question has answers that may be good or bad; the system has marked it active so that they can be reviewed.
















  • Can you add show create table ... for the two tables? The query plan doesn't seem to use any index.

    – Giovanni
    Mar 10 '15 at 13:40











  • Okay, I edited my post.

    – leoj
    Mar 11 '15 at 2:16











  • An index on (category_id, text_id) would help your query more than the ones you have. It would also be good if you provided the whole EXPLAIN output (and not cut some parts off) so we can see which indexes are used.

    – ypercubeᵀᴹ
    Mar 11 '15 at 9:00














2












2








2








I have two tables. One for texts and one to assign those texts to categories. I want to select texts of one specific category and order them by last change date. So, I am using this query:



SELECT 
t2.text_id
FROM
texts_to_categories AS t1,
texts AS t2
WHERE
t1.category_id = 123
AND t2.text_id = t1.text_id
ORDER BY
t2.time_changed DESC
LIMIT 10


I tried a lot of index combinations but I keep getting a temporary and filesort:



id  select_type table   type    possible_keys                   key         key_len ref         rows    extra
1 SIMPLE t1 ref text_id,text_id_2,category_id category_id 5 const 203 Using where; Using temporary; Using filesort
1 SIMPLE t2 eq_ref PRIMARY,text_id PRIMARY 4 text_id 1 Using where


Edit: Here is a CREATE TABLE for the two tables:



CREATE TABLE `texts` (
`text_id` int(11) unsigned NOT NULL AUTO_INCREMENT,
`time_changed` datetime DEFAULT NULL,
PRIMARY KEY (`text_id`),
KEY `time_changed` (`time_changed`)
) ENGINE=InnoDB AUTO_INCREMENT=132207 DEFAULT CHARSET=utf8

CREATE TABLE `texts_to_categories` (
`id` int(11) unsigned NOT NULL AUTO_INCREMENT,
`text_id` int(11) DEFAULT NULL,
`category_id` int(11) DEFAULT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `text_id` (`text_id`,`category_id`),
KEY `text_id_2` (`text_id`),
KEY `category_id` (`category_id`)
) ENGINE=InnoDB AUTO_INCREMENT=740789 DEFAULT CHARSET=utf8









share|improve this question
















I have two tables. One for texts and one to assign those texts to categories. I want to select texts of one specific category and order them by last change date. So, I am using this query:



SELECT 
t2.text_id
FROM
texts_to_categories AS t1,
texts AS t2
WHERE
t1.category_id = 123
AND t2.text_id = t1.text_id
ORDER BY
t2.time_changed DESC
LIMIT 10


I tried a lot of index combinations but I keep getting a temporary and filesort:



id  select_type table   type    possible_keys                   key         key_len ref         rows    extra
1 SIMPLE t1 ref text_id,text_id_2,category_id category_id 5 const 203 Using where; Using temporary; Using filesort
1 SIMPLE t2 eq_ref PRIMARY,text_id PRIMARY 4 text_id 1 Using where


Edit: Here is a CREATE TABLE for the two tables:



CREATE TABLE `texts` (
`text_id` int(11) unsigned NOT NULL AUTO_INCREMENT,
`time_changed` datetime DEFAULT NULL,
PRIMARY KEY (`text_id`),
KEY `time_changed` (`time_changed`)
) ENGINE=InnoDB AUTO_INCREMENT=132207 DEFAULT CHARSET=utf8

CREATE TABLE `texts_to_categories` (
`id` int(11) unsigned NOT NULL AUTO_INCREMENT,
`text_id` int(11) DEFAULT NULL,
`category_id` int(11) DEFAULT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `text_id` (`text_id`,`category_id`),
KEY `text_id_2` (`text_id`),
KEY `category_id` (`category_id`)
) ENGINE=InnoDB AUTO_INCREMENT=740789 DEFAULT CHARSET=utf8






mysql






share|improve this question















share|improve this question













share|improve this question




share|improve this question








edited Mar 11 '15 at 9:30







leoj

















asked Mar 10 '15 at 7:07









leojleoj

112




112





bumped to the homepage by Community 6 mins ago


This question has answers that may be good or bad; the system has marked it active so that they can be reviewed.







bumped to the homepage by Community 6 mins ago


This question has answers that may be good or bad; the system has marked it active so that they can be reviewed.















  • Can you add show create table ... for the two tables? The query plan doesn't seem to use any index.

    – Giovanni
    Mar 10 '15 at 13:40











  • Okay, I edited my post.

    – leoj
    Mar 11 '15 at 2:16











  • An index on (category_id, text_id) would help your query more than the ones you have. It would also be good if you provided the whole EXPLAIN output (and not cut some parts off) so we can see which indexes are used.

    – ypercubeᵀᴹ
    Mar 11 '15 at 9:00



















  • Can you add show create table ... for the two tables? The query plan doesn't seem to use any index.

    – Giovanni
    Mar 10 '15 at 13:40











  • Okay, I edited my post.

    – leoj
    Mar 11 '15 at 2:16











  • An index on (category_id, text_id) would help your query more than the ones you have. It would also be good if you provided the whole EXPLAIN output (and not cut some parts off) so we can see which indexes are used.

    – ypercubeᵀᴹ
    Mar 11 '15 at 9:00

















Can you add show create table ... for the two tables? The query plan doesn't seem to use any index.

– Giovanni
Mar 10 '15 at 13:40





Can you add show create table ... for the two tables? The query plan doesn't seem to use any index.

– Giovanni
Mar 10 '15 at 13:40













Okay, I edited my post.

– leoj
Mar 11 '15 at 2:16





Okay, I edited my post.

– leoj
Mar 11 '15 at 2:16













An index on (category_id, text_id) would help your query more than the ones you have. It would also be good if you provided the whole EXPLAIN output (and not cut some parts off) so we can see which indexes are used.

– ypercubeᵀᴹ
Mar 11 '15 at 9:00





An index on (category_id, text_id) would help your query more than the ones you have. It would also be good if you provided the whole EXPLAIN output (and not cut some parts off) so we can see which indexes are used.

– ypercubeᵀᴹ
Mar 11 '15 at 9:00










1 Answer
1






active

oldest

votes


















0














You can try to add an index on time_changed:



alter table texts add index (time_changed);


this could get rid of Using temporary and filesort. But you need to define indexes for your query because the query plan show Using where instead of more healthy Using index.





Updated



Maybe the main culprit for the temporary/filesort is the order of the join. It is not good practice to force the optimizer without a good reason, but you could try to force the join order to test if the temporary/filesort goes away. I have swapped the tables and added a straight_join clause:



SELECT straight_join
t2.text_id
FROM
texts AS t2,
texts_to_categories AS t1
WHERE
t1.category_id = 123
AND t2.text_id = t1.text_id
ORDER BY
t2.time_changed DESC
LIMIT 10;


Let me know what is the query plan of the previous query.



I don't think that temporary/filesort is a big deal for few hundred rows. I would let the optimizer do its job. I would be more worried to get a better tables schema. If it is feasible for you, I suggest the following changes to your schema.



For texts_categories your table permits NULL value for text_id and for category_id. So I would delete NULL values:



delete from texts_to_categories  where category_id is NULL or text_id is NULL;

alter table texts_to_categories
change category_id category_id int unsigned not null,
change text_id text_id int unsigned not null;


Next if you don't need texts_categories.id column, I would get rid of it, and I would reorganize indexes:



alter table texts_to_categories
drop column id,
add primary key category_text (category_id, text_id),
drop index text_id,
drop index category_id,
add index text_id;


For table texts I will try time_changed column to do not permit null values:



update texts_bck 
set time_changed = '2010-01-01' -- some default
where time_changed is NULL;


alter table texts
change column time_changed time_changed datetime not null
default current_timestamp;


I hope this is of help.






share|improve this answer

























    Your Answer








    StackExchange.ready(function() {
    var channelOptions = {
    tags: "".split(" "),
    id: "182"
    };
    initTagRenderer("".split(" "), "".split(" "), channelOptions);

    StackExchange.using("externalEditor", function() {
    // Have to fire editor after snippets, if snippets enabled
    if (StackExchange.settings.snippets.snippetsEnabled) {
    StackExchange.using("snippets", function() {
    createEditor();
    });
    }
    else {
    createEditor();
    }
    });

    function createEditor() {
    StackExchange.prepareEditor({
    heartbeatType: 'answer',
    autoActivateHeartbeat: false,
    convertImagesToLinks: false,
    noModals: true,
    showLowRepImageUploadWarning: true,
    reputationToPostImages: null,
    bindNavPrevention: true,
    postfix: "",
    imageUploader: {
    brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
    contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
    allowUrls: true
    },
    onDemand: true,
    discardSelector: ".discard-answer"
    ,immediatelyShowMarkdownHelp:true
    });


    }
    });














    draft saved

    draft discarded


















    StackExchange.ready(
    function () {
    StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fdba.stackexchange.com%2fquestions%2f94832%2fcant-get-rid-of-filesort-in-simple-query%23new-answer', 'question_page');
    }
    );

    Post as a guest















    Required, but never shown

























    1 Answer
    1






    active

    oldest

    votes








    1 Answer
    1






    active

    oldest

    votes









    active

    oldest

    votes






    active

    oldest

    votes









    0














    You can try to add an index on time_changed:



    alter table texts add index (time_changed);


    this could get rid of Using temporary and filesort. But you need to define indexes for your query because the query plan show Using where instead of more healthy Using index.





    Updated



    Maybe the main culprit for the temporary/filesort is the order of the join. It is not good practice to force the optimizer without a good reason, but you could try to force the join order to test if the temporary/filesort goes away. I have swapped the tables and added a straight_join clause:



    SELECT straight_join
    t2.text_id
    FROM
    texts AS t2,
    texts_to_categories AS t1
    WHERE
    t1.category_id = 123
    AND t2.text_id = t1.text_id
    ORDER BY
    t2.time_changed DESC
    LIMIT 10;


    Let me know what is the query plan of the previous query.



    I don't think that temporary/filesort is a big deal for few hundred rows. I would let the optimizer do its job. I would be more worried to get a better tables schema. If it is feasible for you, I suggest the following changes to your schema.



    For texts_categories your table permits NULL value for text_id and for category_id. So I would delete NULL values:



    delete from texts_to_categories  where category_id is NULL or text_id is NULL;

    alter table texts_to_categories
    change category_id category_id int unsigned not null,
    change text_id text_id int unsigned not null;


    Next if you don't need texts_categories.id column, I would get rid of it, and I would reorganize indexes:



    alter table texts_to_categories
    drop column id,
    add primary key category_text (category_id, text_id),
    drop index text_id,
    drop index category_id,
    add index text_id;


    For table texts I will try time_changed column to do not permit null values:



    update texts_bck 
    set time_changed = '2010-01-01' -- some default
    where time_changed is NULL;


    alter table texts
    change column time_changed time_changed datetime not null
    default current_timestamp;


    I hope this is of help.






    share|improve this answer






























      0














      You can try to add an index on time_changed:



      alter table texts add index (time_changed);


      this could get rid of Using temporary and filesort. But you need to define indexes for your query because the query plan show Using where instead of more healthy Using index.





      Updated



      Maybe the main culprit for the temporary/filesort is the order of the join. It is not good practice to force the optimizer without a good reason, but you could try to force the join order to test if the temporary/filesort goes away. I have swapped the tables and added a straight_join clause:



      SELECT straight_join
      t2.text_id
      FROM
      texts AS t2,
      texts_to_categories AS t1
      WHERE
      t1.category_id = 123
      AND t2.text_id = t1.text_id
      ORDER BY
      t2.time_changed DESC
      LIMIT 10;


      Let me know what is the query plan of the previous query.



      I don't think that temporary/filesort is a big deal for few hundred rows. I would let the optimizer do its job. I would be more worried to get a better tables schema. If it is feasible for you, I suggest the following changes to your schema.



      For texts_categories your table permits NULL value for text_id and for category_id. So I would delete NULL values:



      delete from texts_to_categories  where category_id is NULL or text_id is NULL;

      alter table texts_to_categories
      change category_id category_id int unsigned not null,
      change text_id text_id int unsigned not null;


      Next if you don't need texts_categories.id column, I would get rid of it, and I would reorganize indexes:



      alter table texts_to_categories
      drop column id,
      add primary key category_text (category_id, text_id),
      drop index text_id,
      drop index category_id,
      add index text_id;


      For table texts I will try time_changed column to do not permit null values:



      update texts_bck 
      set time_changed = '2010-01-01' -- some default
      where time_changed is NULL;


      alter table texts
      change column time_changed time_changed datetime not null
      default current_timestamp;


      I hope this is of help.






      share|improve this answer




























        0












        0








        0







        You can try to add an index on time_changed:



        alter table texts add index (time_changed);


        this could get rid of Using temporary and filesort. But you need to define indexes for your query because the query plan show Using where instead of more healthy Using index.





        Updated



        Maybe the main culprit for the temporary/filesort is the order of the join. It is not good practice to force the optimizer without a good reason, but you could try to force the join order to test if the temporary/filesort goes away. I have swapped the tables and added a straight_join clause:



        SELECT straight_join
        t2.text_id
        FROM
        texts AS t2,
        texts_to_categories AS t1
        WHERE
        t1.category_id = 123
        AND t2.text_id = t1.text_id
        ORDER BY
        t2.time_changed DESC
        LIMIT 10;


        Let me know what is the query plan of the previous query.



        I don't think that temporary/filesort is a big deal for few hundred rows. I would let the optimizer do its job. I would be more worried to get a better tables schema. If it is feasible for you, I suggest the following changes to your schema.



        For texts_categories your table permits NULL value for text_id and for category_id. So I would delete NULL values:



        delete from texts_to_categories  where category_id is NULL or text_id is NULL;

        alter table texts_to_categories
        change category_id category_id int unsigned not null,
        change text_id text_id int unsigned not null;


        Next if you don't need texts_categories.id column, I would get rid of it, and I would reorganize indexes:



        alter table texts_to_categories
        drop column id,
        add primary key category_text (category_id, text_id),
        drop index text_id,
        drop index category_id,
        add index text_id;


        For table texts I will try time_changed column to do not permit null values:



        update texts_bck 
        set time_changed = '2010-01-01' -- some default
        where time_changed is NULL;


        alter table texts
        change column time_changed time_changed datetime not null
        default current_timestamp;


        I hope this is of help.






        share|improve this answer















        You can try to add an index on time_changed:



        alter table texts add index (time_changed);


        this could get rid of Using temporary and filesort. But you need to define indexes for your query because the query plan show Using where instead of more healthy Using index.





        Updated



        Maybe the main culprit for the temporary/filesort is the order of the join. It is not good practice to force the optimizer without a good reason, but you could try to force the join order to test if the temporary/filesort goes away. I have swapped the tables and added a straight_join clause:



        SELECT straight_join
        t2.text_id
        FROM
        texts AS t2,
        texts_to_categories AS t1
        WHERE
        t1.category_id = 123
        AND t2.text_id = t1.text_id
        ORDER BY
        t2.time_changed DESC
        LIMIT 10;


        Let me know what is the query plan of the previous query.



        I don't think that temporary/filesort is a big deal for few hundred rows. I would let the optimizer do its job. I would be more worried to get a better tables schema. If it is feasible for you, I suggest the following changes to your schema.



        For texts_categories your table permits NULL value for text_id and for category_id. So I would delete NULL values:



        delete from texts_to_categories  where category_id is NULL or text_id is NULL;

        alter table texts_to_categories
        change category_id category_id int unsigned not null,
        change text_id text_id int unsigned not null;


        Next if you don't need texts_categories.id column, I would get rid of it, and I would reorganize indexes:



        alter table texts_to_categories
        drop column id,
        add primary key category_text (category_id, text_id),
        drop index text_id,
        drop index category_id,
        add index text_id;


        For table texts I will try time_changed column to do not permit null values:



        update texts_bck 
        set time_changed = '2010-01-01' -- some default
        where time_changed is NULL;


        alter table texts
        change column time_changed time_changed datetime not null
        default current_timestamp;


        I hope this is of help.







        share|improve this answer














        share|improve this answer



        share|improve this answer








        edited Mar 11 '15 at 13:57

























        answered Mar 10 '15 at 13:47









        GiovanniGiovanni

        822514




        822514






























            draft saved

            draft discarded




















































            Thanks for contributing an answer to Database Administrators Stack Exchange!


            • Please be sure to answer the question. Provide details and share your research!

            But avoid



            • Asking for help, clarification, or responding to other answers.

            • Making statements based on opinion; back them up with references or personal experience.


            To learn more, see our tips on writing great answers.




            draft saved


            draft discarded














            StackExchange.ready(
            function () {
            StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fdba.stackexchange.com%2fquestions%2f94832%2fcant-get-rid-of-filesort-in-simple-query%23new-answer', 'question_page');
            }
            );

            Post as a guest















            Required, but never shown





















































            Required, but never shown














            Required, but never shown












            Required, but never shown







            Required, but never shown

































            Required, but never shown














            Required, but never shown












            Required, but never shown







            Required, but never shown







            Popular posts from this blog

            Szabolcs (Ungheria) Altri progetti | Menu di navigazione48°10′14.56″N 21°29′33.14″E /...

            Discografia di Klaus Schulze Indice Album in studio | Album dal vivo | Singoli | Antologie | Colonne...

            How to make inet_server_addr() return localhost in spite of ::1/128RETURN NEXT in Postgres FunctionConnect to...