On Saturday, 30 January 2021 at 14:56:14 UTC, burt wrote:
On Saturday, 30 January 2021 at 14:41:59 UTC, Afgdr wrote:
On Saturday, 30 January 2021 at 14:40:49 UTC, Afgdr wrote:
On Saturday, 30 January 2021 at 13:30:49 UTC, burt wrote:
[...]

cast as uint and shift. cast the result as ubyte[4].

obiously, that works for n=4 with uint and n=8 for ulong, only.

Yes I used to do this, but then I needed it for n > 8.

You can try somethink like this:

https://run.dlang.io/is/POQgnb

import std.range : cycle, take, drop;
import std.algorithm : copy;
import std.stdio;

version (LittleEndian)
ubyte[n] rotateRight(size_t n)(ref const ubyte[n] array, uint rotation){
    typeof(return) result;

    array[]
        .cycle()
        .drop(n - (rotation / 8) % n)
        .take(n)
        .copy(result[]);

    const ubyte bit_rotation = rotation % 8;

    enum ubyte full = 0b1111_1111;

    if(bit_rotation == 0)
        return result;

    ubyte next_prefix(const ubyte elm){
        const ubyte suffix = (elm & ~(full << bit_rotation));
const ubyte prefix = cast(ubyte)(suffix << (8 - bit_rotation));
        return prefix;
    }

    ubyte prefix = next_prefix(result[$-1]);

    foreach(ref ubyte elm; result[]){
        const new_prefix = next_prefix(elm);
        elm = (elm >> bit_rotation) | prefix;
        prefix = new_prefix;
    }

    return result;
}

void main(){
    ubyte[4] x = [
        0b00011000,
        0b00100001,
        0b00010101,
        0b11110010,
    ];

        writefln!"%(%8b,\n%)"(x.rotateRight(4));
}

Reply via email to