Generating random N-dimensional arrays

The name of the pictureThe name of the pictureThe name of the pictureClash Royale CLAN TAG#URR8PPP





.everyoneloves__top-leaderboard:empty,.everyoneloves__mid-leaderboard:empty margin-bottom:0;







up vote
2
down vote

favorite












For this code challenge, I want to create a performant function that creates a rectangular N-dimensional array. (min_dim_size, max_dim_size) is the span size of every dimension. So rectangular_properties is a list with sizes of every dimension of the matrix. The matrix contains random integer values. Also I want the matrix to be immutable on every dimension.



Now I have this code:



def random_hyperrectangular_matrix(dimensions, min_dim_size, max_dim_size):
rectangular_properties = [randint(min_dim_size, max_dim_size) for _ in range(dimensions)]
def recc2(dim):
if dim == 0:
return randint(0, 100)
return tuple([recc2(dim - 1) for _ in range(rectangular_properties[dim - 1])])
random_n_dimensional_matrix = recc2(dimensions)
return random_n_dimensional_matrix


When I run my code it seems that the generation of this matrix takes a huge amount of time. Is there a lack of performance in it?
Does the generation of tuple([...]) out of a list takes much time?







share|improve this question



























    up vote
    2
    down vote

    favorite












    For this code challenge, I want to create a performant function that creates a rectangular N-dimensional array. (min_dim_size, max_dim_size) is the span size of every dimension. So rectangular_properties is a list with sizes of every dimension of the matrix. The matrix contains random integer values. Also I want the matrix to be immutable on every dimension.



    Now I have this code:



    def random_hyperrectangular_matrix(dimensions, min_dim_size, max_dim_size):
    rectangular_properties = [randint(min_dim_size, max_dim_size) for _ in range(dimensions)]
    def recc2(dim):
    if dim == 0:
    return randint(0, 100)
    return tuple([recc2(dim - 1) for _ in range(rectangular_properties[dim - 1])])
    random_n_dimensional_matrix = recc2(dimensions)
    return random_n_dimensional_matrix


    When I run my code it seems that the generation of this matrix takes a huge amount of time. Is there a lack of performance in it?
    Does the generation of tuple([...]) out of a list takes much time?







    share|improve this question























      up vote
      2
      down vote

      favorite









      up vote
      2
      down vote

      favorite











      For this code challenge, I want to create a performant function that creates a rectangular N-dimensional array. (min_dim_size, max_dim_size) is the span size of every dimension. So rectangular_properties is a list with sizes of every dimension of the matrix. The matrix contains random integer values. Also I want the matrix to be immutable on every dimension.



      Now I have this code:



      def random_hyperrectangular_matrix(dimensions, min_dim_size, max_dim_size):
      rectangular_properties = [randint(min_dim_size, max_dim_size) for _ in range(dimensions)]
      def recc2(dim):
      if dim == 0:
      return randint(0, 100)
      return tuple([recc2(dim - 1) for _ in range(rectangular_properties[dim - 1])])
      random_n_dimensional_matrix = recc2(dimensions)
      return random_n_dimensional_matrix


      When I run my code it seems that the generation of this matrix takes a huge amount of time. Is there a lack of performance in it?
      Does the generation of tuple([...]) out of a list takes much time?







      share|improve this question













      For this code challenge, I want to create a performant function that creates a rectangular N-dimensional array. (min_dim_size, max_dim_size) is the span size of every dimension. So rectangular_properties is a list with sizes of every dimension of the matrix. The matrix contains random integer values. Also I want the matrix to be immutable on every dimension.



      Now I have this code:



      def random_hyperrectangular_matrix(dimensions, min_dim_size, max_dim_size):
      rectangular_properties = [randint(min_dim_size, max_dim_size) for _ in range(dimensions)]
      def recc2(dim):
      if dim == 0:
      return randint(0, 100)
      return tuple([recc2(dim - 1) for _ in range(rectangular_properties[dim - 1])])
      random_n_dimensional_matrix = recc2(dimensions)
      return random_n_dimensional_matrix


      When I run my code it seems that the generation of this matrix takes a huge amount of time. Is there a lack of performance in it?
      Does the generation of tuple([...]) out of a list takes much time?









      share|improve this question












      share|improve this question




      share|improve this question








      edited Jul 16 at 21:44









      200_success

      123k14143399




      123k14143399









      asked Jul 16 at 20:56









      S.G.

      217112




      217112




















          1 Answer
          1






          active

          oldest

          votes

















          up vote
          3
          down vote













          For something like this, numpy is probably unbeatable in terms of performance, since its underlying functions are implemented in C.



          In your case the implementation would be rather easy:



          import numpy as np

          def random_hyperrectangular_matrix(dimensions, min_dim_size, max_dim_size):
          shape = np.random.randint(min_dim_size, max_dim_size + 1, dimensions)
          return np.random.randint(0, 101, shape)


          Note the +1 on the upper limits, since np.random.randint excludes the upper bound, whereas random.randint includes it.



          Note also that dimensions is in this case limited to be less than or equal to 32 (because of limits in the internal implementation). Your algorithm will only fail once the recursion depth reaches the limit (1000 by default). But if you need more than 32 dimensions, you are probably doing something wrong, anyways...



          This might also make the rest of your program (which you don't show) easier, because operations can act on each element of the array, or only certain dimensions.




          With min_dim_size, max_dim_size = 2, 2 (the lowest practical numbers, and the same to eliminate one source of randomness in the timings) this consistently improves the timing (note the logarithmic scale on the y-axis):



          enter image description here



          Especially noteworthy is that at low dimensions, the numpy approach is basically constant in time. For higher dimensions it scales the same as your approach, but consistently lower.






          share|improve this answer























            Your Answer




            StackExchange.ifUsing("editor", function ()
            return StackExchange.using("mathjaxEditing", function ()
            StackExchange.MarkdownEditor.creationCallbacks.add(function (editor, postfix)
            StackExchange.mathjaxEditing.prepareWmdForMathJax(editor, postfix, [["\$", "\$"]]);
            );
            );
            , "mathjax-editing");

            StackExchange.ifUsing("editor", function ()
            StackExchange.using("externalEditor", function ()
            StackExchange.using("snippets", function ()
            StackExchange.snippets.init();
            );
            );
            , "code-snippets");

            StackExchange.ready(function()
            var channelOptions =
            tags: "".split(" "),
            id: "196"
            ;
            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',
            convertImagesToLinks: false,
            noModals: false,
            showLowRepImageUploadWarning: true,
            reputationToPostImages: null,
            bindNavPrevention: true,
            postfix: "",
            onDemand: true,
            discardSelector: ".discard-answer"
            ,immediatelyShowMarkdownHelp:true
            );



            );








             

            draft saved


            draft discarded


















            StackExchange.ready(
            function ()
            StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fcodereview.stackexchange.com%2fquestions%2f199627%2fgenerating-random-n-dimensional-arrays%23new-answer', 'question_page');

            );

            Post as a guest






























            1 Answer
            1






            active

            oldest

            votes








            1 Answer
            1






            active

            oldest

            votes









            active

            oldest

            votes






            active

            oldest

            votes








            up vote
            3
            down vote













            For something like this, numpy is probably unbeatable in terms of performance, since its underlying functions are implemented in C.



            In your case the implementation would be rather easy:



            import numpy as np

            def random_hyperrectangular_matrix(dimensions, min_dim_size, max_dim_size):
            shape = np.random.randint(min_dim_size, max_dim_size + 1, dimensions)
            return np.random.randint(0, 101, shape)


            Note the +1 on the upper limits, since np.random.randint excludes the upper bound, whereas random.randint includes it.



            Note also that dimensions is in this case limited to be less than or equal to 32 (because of limits in the internal implementation). Your algorithm will only fail once the recursion depth reaches the limit (1000 by default). But if you need more than 32 dimensions, you are probably doing something wrong, anyways...



            This might also make the rest of your program (which you don't show) easier, because operations can act on each element of the array, or only certain dimensions.




            With min_dim_size, max_dim_size = 2, 2 (the lowest practical numbers, and the same to eliminate one source of randomness in the timings) this consistently improves the timing (note the logarithmic scale on the y-axis):



            enter image description here



            Especially noteworthy is that at low dimensions, the numpy approach is basically constant in time. For higher dimensions it scales the same as your approach, but consistently lower.






            share|improve this answer



























              up vote
              3
              down vote













              For something like this, numpy is probably unbeatable in terms of performance, since its underlying functions are implemented in C.



              In your case the implementation would be rather easy:



              import numpy as np

              def random_hyperrectangular_matrix(dimensions, min_dim_size, max_dim_size):
              shape = np.random.randint(min_dim_size, max_dim_size + 1, dimensions)
              return np.random.randint(0, 101, shape)


              Note the +1 on the upper limits, since np.random.randint excludes the upper bound, whereas random.randint includes it.



              Note also that dimensions is in this case limited to be less than or equal to 32 (because of limits in the internal implementation). Your algorithm will only fail once the recursion depth reaches the limit (1000 by default). But if you need more than 32 dimensions, you are probably doing something wrong, anyways...



              This might also make the rest of your program (which you don't show) easier, because operations can act on each element of the array, or only certain dimensions.




              With min_dim_size, max_dim_size = 2, 2 (the lowest practical numbers, and the same to eliminate one source of randomness in the timings) this consistently improves the timing (note the logarithmic scale on the y-axis):



              enter image description here



              Especially noteworthy is that at low dimensions, the numpy approach is basically constant in time. For higher dimensions it scales the same as your approach, but consistently lower.






              share|improve this answer

























                up vote
                3
                down vote










                up vote
                3
                down vote









                For something like this, numpy is probably unbeatable in terms of performance, since its underlying functions are implemented in C.



                In your case the implementation would be rather easy:



                import numpy as np

                def random_hyperrectangular_matrix(dimensions, min_dim_size, max_dim_size):
                shape = np.random.randint(min_dim_size, max_dim_size + 1, dimensions)
                return np.random.randint(0, 101, shape)


                Note the +1 on the upper limits, since np.random.randint excludes the upper bound, whereas random.randint includes it.



                Note also that dimensions is in this case limited to be less than or equal to 32 (because of limits in the internal implementation). Your algorithm will only fail once the recursion depth reaches the limit (1000 by default). But if you need more than 32 dimensions, you are probably doing something wrong, anyways...



                This might also make the rest of your program (which you don't show) easier, because operations can act on each element of the array, or only certain dimensions.




                With min_dim_size, max_dim_size = 2, 2 (the lowest practical numbers, and the same to eliminate one source of randomness in the timings) this consistently improves the timing (note the logarithmic scale on the y-axis):



                enter image description here



                Especially noteworthy is that at low dimensions, the numpy approach is basically constant in time. For higher dimensions it scales the same as your approach, but consistently lower.






                share|improve this answer















                For something like this, numpy is probably unbeatable in terms of performance, since its underlying functions are implemented in C.



                In your case the implementation would be rather easy:



                import numpy as np

                def random_hyperrectangular_matrix(dimensions, min_dim_size, max_dim_size):
                shape = np.random.randint(min_dim_size, max_dim_size + 1, dimensions)
                return np.random.randint(0, 101, shape)


                Note the +1 on the upper limits, since np.random.randint excludes the upper bound, whereas random.randint includes it.



                Note also that dimensions is in this case limited to be less than or equal to 32 (because of limits in the internal implementation). Your algorithm will only fail once the recursion depth reaches the limit (1000 by default). But if you need more than 32 dimensions, you are probably doing something wrong, anyways...



                This might also make the rest of your program (which you don't show) easier, because operations can act on each element of the array, or only certain dimensions.




                With min_dim_size, max_dim_size = 2, 2 (the lowest practical numbers, and the same to eliminate one source of randomness in the timings) this consistently improves the timing (note the logarithmic scale on the y-axis):



                enter image description here



                Especially noteworthy is that at low dimensions, the numpy approach is basically constant in time. For higher dimensions it scales the same as your approach, but consistently lower.







                share|improve this answer















                share|improve this answer



                share|improve this answer








                edited Jul 17 at 9:54


























                answered Jul 17 at 9:34









                Graipher

                20.4k42981




                20.4k42981






















                     

                    draft saved


                    draft discarded


























                     


                    draft saved


                    draft discarded














                    StackExchange.ready(
                    function ()
                    StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fcodereview.stackexchange.com%2fquestions%2f199627%2fgenerating-random-n-dimensional-arrays%23new-answer', 'question_page');

                    );

                    Post as a guest













































































                    Popular posts from this blog

                    Chat program with C++ and SFML

                    Function to Return a JSON Like Objects Using VBA Collections and Arrays

                    Will my employers contract hold up in court?