Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    primarykey
    data
    text
    <p>Here's a quick &amp; cheesy implementation to get you going until a good one comes along:</p> <pre><code>def mortanize(x, y) xs, ys = [x, y].map do |n| n.to_s(2) end nbits = [xs, ys].map(&amp;:size).max xs, ys = [xs, ys].map do |n| ('0' * (nbits - n.size) + n).chars end ys.zip(xs).join.to_i(2) end </code></pre> <p>As you might expect, it's no speed deamon. On my box, with MRI 1.8.7, it computes about 35,000 16-bit results per second. Yours computes 68,000 16-bit results per second. Or, see the next algorithm for 256,000 16-bit results per second.</p> <hr> <p>If you're willing to trade a little memory and startup time for speed, then:</p> <pre><code>def base_mortanize(x, y) xs, ys = [x, y].map do |n| n.to_s(2) end nbits = [xs, ys].map(&amp;:size).max xs, ys = [xs, ys].map do |n| ('0' * (nbits - n.size) + n).chars end ys.zip(xs).join.to_i(2) end MORTON_TABLE_X = 256.times.map do |x| base_mortanize(x, 0) end MORTON_TABLE_Y = 256.times.map do |y| base_mortanize(0, y) end def mortanize(x, y) z = [] while (x &gt; 0 || y &gt; 0) z &lt;&lt; (MORTON_TABLE_X[x &amp; 0xff] | MORTON_TABLE_Y[y &amp; 0xff]) x &gt;&gt;= 8 y &gt;&gt;= 8 end z.reverse.inject(0) do |result, word| result &lt;&lt; 16 | word end end </code></pre> <p>This one computes 256,000 16-bit results per second.</p> <hr> <p>There's a bug in your answer if either argument is zero. Here's one possible fix for it. First define this function:</p> <pre><code>def bit_size(x) return 1 if x == 0 Math.log2(x).floor + 1 end </code></pre> <p>And then, inside <code>interleave</code>, replace:</p> <pre><code>z, bl, ybl = 0, (Math.log2(self)).floor + 1, (Math.log2(y)).floor + 1 </code></pre> <p>with:</p> <pre><code>z = 0 bl = bit_size(x) ybl = bit_size(y) </code></pre> <hr> <p>Here is the rspec test case I used:</p> <pre><code>describe "mortanize" do it "should interleave integers" do mortanize(0, 0).should eql 0 mortanize(0, 1).should eql 2 mortanize(1, 0).should eql 1 mortanize(0xf, 0x3).should eql 0x5f mortanize(0x3, 0xf).should eql 0xaf mortanize(0xf, 0x0).should eql 0x55 mortanize(0x0, 0xf).should eql 0xaa mortanize(0x3, 0xc).should eql 0xa5 mortanize(0xf, 0xf).should eql 0xff mortanize(0x1234, 0x4321).should eql 0x210e0d12 end end </code></pre>
    singulars
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. VO
      singulars
      1. This table or related slice is empty.
    2. VO
      singulars
      1. This table or related slice is empty.
    3. VO
      singulars
      1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload