Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- <Query Kind="Program">
- <Reference><RuntimeDirectory>\System.Drawing.dll</Reference>
- <Namespace>System.Drawing</Namespace>
- </Query>
- void Main()
- {
- var roomDescs = new RoomsProvider();
- roomDescs.Load(@"C:\Users\Admin\Documents\isaac\levelgen\resources\rooms");
- var bot1Total = new int[14];
- var bot2Total = new int[14];
- foreach (var fp in new DirectoryInfo(@"C:\Users\Admin\Documents\isaac\levelgen\dump2").GetFiles())
- {
- using (var file = File.OpenRead(fp.FullName))
- {
- Console.WriteLine(file.Name);
- var reader = new LayoutReader(file, roomDescs);
- StageBlock sb;
- while ((sb = reader.Read()) != null)
- {
- for (var i = 0; i < sb.Stages.Length; i++)
- {
- if (sb.Stages[i].StageId == 9 || sb.Stages[i].StageId == 12 || (sb.Stages[i].StageId == 10 && sb.Stages[i].StageType == 1) || (sb.Stages[i].StageId == 11 && sb.Stages[i].StageType == 1))
- continue;
- var seedStr = SeedToString(sb.Seed);
- //Console.WriteLine("{0} (Stage {1})", SeedToString(sb.Seed), sb.Stages[i].StageId);
- //Console.WriteLine("--------");
- Func<Room, string> roomToChar = (room) =>
- {
- if (room == null)
- return "O";
- if (room.StageIndex == 0 && room.RoomType == RoomType.ROOM_DEFAULT && room.RoomId == 2)
- return "S";
- if (room.RoomType == RoomType.ROOM_BOSS)
- return "B";
- return "X";
- };
- for (var y = 0; y < 13; y++)
- {
- var line = string.Join("", Enumerable.Range(0, 13).Select(k => roomToChar(sb.Stages[i].RoomGrid[y][k])));
- //Console.WriteLine(line);
- }
- var bot = new Bot1();
- bot.Start(sb.Stages[i]);
- do
- {
- } while (bot.Think());
- var bot2 = new Bot2();
- bot2.Start(sb.Stages[i]);
- do
- {
- } while (bot2.Think());
- //Console.WriteLine(bot.RoomsVisited);
- //Console.WriteLine(bot2.RoomsVisited);
- bot1Total[sb.Stages[i].StageId] += bot.RoomsVisited;
- bot2Total[sb.Stages[i].StageId] += bot2.RoomsVisited;
- }
- }
- }
- }
- bot1Total.Dump();
- bot2Total.Dump();
- }
- public class RoomState
- {
- public bool Visited = false;
- public bool Revealed = false;
- public Room Room;
- }
- public class BotState
- {
- public Stage Stage;
- public Point Pos;
- public RoomState[][] GridState;
- public Room CurrentRoom { get { return GridState[Pos.Y][Pos.X].Room; }}
- public BotState(Stage stage)
- {
- Stage = stage;
- GridState = new RoomState[13][];
- for (var j = 0; j < GridState.Length; j++)
- GridState[j] = new RoomState[13];
- var gridStateArr = new RoomState[Stage.Rooms.Length];
- for (var y = 0; y < 13; y++)
- {
- for (var x = 0; x < 13; x++)
- {
- var room = stage.RoomGrid[y][x];
- if (room == null)
- {
- GridState[y][x] = new RoomState();
- continue;
- }
- var state = gridStateArr[room.RoomOffset] ?? new RoomState { Room = room};
- gridStateArr[room.RoomOffset] = state;
- GridState[y][x] = state;
- }
- }
- }
- }
- public abstract class Bot
- {
- public BotState State;
- public Room[][] Grid { get { return State.Stage.RoomGrid; } }
- public RoomState[][] GridState { get { return State.GridState; } }
- public Point GetStart()
- {
- for (var y = 0; y < 13; y++)
- {
- for (var x = 0; x < 13; x++)
- {
- var room = Grid[y][x];
- if (room == null)
- continue;
- if (room.StageIndex == 0 && room.RoomType == RoomType.ROOM_DEFAULT && room.RoomId == 2 //Standard start room
- || ((room.StageIndex == 16 || room.StageIndex == 17) && room.RoomType == RoomType.ROOM_DEFAULT && room.RoomId == 0)) //Chest/DarkRoom start rooms
- {
- return new Point(x, y);
- }
- }
- }
- throw new Exception("Start room not found D:");
- }
- public Point GetEnd()
- {
- for (var y = 0; y < 13; y++)
- {
- for (var x = 0; x < 13; x++)
- {
- var room = Grid[y][x];
- if (room == null)
- continue;
- if (room.RoomType == RoomType.ROOM_BOSS)
- {
- return new Point(x, y);
- }
- }
- }
- throw new Exception("Boss room not found D:");
- }
- public virtual void Start(Stage stage)
- {
- State = new BotState(stage);
- State.Pos = GetStart();
- }
- public abstract bool Think();
- public virtual void End()
- {
- }
- public static bool InBounds(Point p)
- {
- return p.X >= 0 && p.Y >= 0 && p.X < 13 && p.Y < 13;
- }
- //The points are using the top/left most grid x/y.
- #region shape doors
- public static Dictionary<RoomShape, Point[]> ShapeDoors = new Dictionary<UserQuery.RoomShape, System.Drawing.Point[]>
- {
- // U R D L, U R D L
- {RoomShape.ROOMSHAPE_1x1, new [] { new Point(0, -1), new Point(1, 0), new Point(0, 1), new Point(-1, 0), default(Point), default(Point), default(Point), default(Point) } },
- {RoomShape.ROOMSHAPE_1x2, new [] { new Point(0, -1), new Point(1, 0), new Point(0, 2), new Point(-1, 0), default(Point), new Point(1, 1), default(Point), new Point(-1, 1) } },
- {RoomShape.ROOMSHAPE_2x1, new [] { new Point(0, -1), new Point(2, 0), new Point(0, 1), new Point(-1, 0), new Point(1, -1), default(Point), new Point(1, 1), default(Point) } },
- {RoomShape.ROOMSHAPE_2x2, new [] { new Point(0, -1), new Point(2, 0), new Point(0, 2), new Point(-1, 0), new Point(1, -1), new Point(2, 1), new Point(1, 2), new Point(-1, 1)} },
- {RoomShape.ROOMSHAPE_IH, new [] { default(Point), new Point(1, 0), default(Point), new Point(-1, 0) , default(Point), default(Point), default(Point), default(Point) } },
- {RoomShape.ROOMSHAPE_IIH, new [] { default(Point), new Point(2, 0), default(Point), new Point(-1, 0) , default(Point), default(Point), default(Point), default(Point) } },
- {RoomShape.ROOMSHAPE_IV, new [] { new Point(0, -1), default(Point), new Point(0, 1), default(Point), default(Point), default(Point), default(Point), default(Point) } },
- {RoomShape.ROOMSHAPE_IIV, new [] { new Point(0, -1), default(Point), new Point(0, 2), default(Point), default(Point), default(Point), default(Point), default(Point) } },
- {RoomShape.ROOMSHAPE_LTL, new [] { new Point(-1, 0), new Point(1, 0), new Point(-1, 2), new Point(-1, 0), new Point(0, -1), new Point(1, 1), new Point(0, 2), new Point(-2, 1) } },
- {RoomShape.ROOMSHAPE_LTR, new [] { new Point(0, -1), new Point(1, 0), new Point(0, 2), new Point(-1, 0), new Point(1, 0), new Point(2, 1), new Point(1, 2), new Point(-1, 1) } },
- {RoomShape.ROOMSHAPE_LBL, new [] { new Point(0, -1), new Point(2, 0), new Point(0, 1), new Point(-1, 0), new Point(1, -1), new Point(2, 1), new Point(1, 2), new Point(0,-1) } },
- {RoomShape.ROOMSHAPE_LBR, new [] { new Point(0, -1), new Point(2, 0), new Point(0, 2), new Point(-1, 0), new Point(1, -1), new Point(1, 1), new Point(1, 1), new Point(-1, 1) } },
- };
- #endregion
- }
- public class Bot1 : Bot
- {
- Stack<Point> Visited = new Stack<System.Drawing.Point>();
- public int RoomsVisited;
- static RoomState[] exitRooms = new RoomState[8];
- #region weights
- static Dictionary<RoomShape, float> ShapeWeights = new Dictionary<UserQuery.RoomShape, float>
- {
- {RoomShape.ROOMSHAPE_1x1, 1},
- {RoomShape.ROOMSHAPE_1x2, 1.5f},
- {RoomShape.ROOMSHAPE_2x1, 1.5f},
- {RoomShape.ROOMSHAPE_2x2, 2},
- {RoomShape.ROOMSHAPE_IH, 1f},
- {RoomShape.ROOMSHAPE_IIH, 1.5f},
- {RoomShape.ROOMSHAPE_IIV, 1.5f},
- {RoomShape.ROOMSHAPE_IV, 1f},
- {RoomShape.ROOMSHAPE_LBL, 1.75f},
- {RoomShape.ROOMSHAPE_LBR, 1.75f},
- {RoomShape.ROOMSHAPE_LTL, 1.75f},
- {RoomShape.ROOMSHAPE_LTR, 1.75f},
- };
- #endregion
- void RevealRooms()
- {
- //Revealing secret rooms is fine for now since we don't actually enter them.
- GridState[State.Pos.Y][State.Pos.X].Revealed = true;
- var exits = ShapeDoors[State.CurrentRoom.Shape];
- for (var i = 0; i < exits.Length; i++)
- {
- if (exits[i] == default(Point))
- continue;
- var dstP = State.Pos.Add(exits[i]);
- if (!InBounds(dstP))
- continue;
- var dstRoom = State.GridState[dstP.Y][dstP.X];
- dstRoom.Revealed = true;
- }
- }
- bool IsPossible(Point pos, HashSet<Point> visited)
- {
- var room = State.GridState[pos.Y][pos.X];
- if (!room.Revealed)
- return true;
- if (room.Revealed && room.Room == null)
- return false;
- visited.Add(pos);
- var exits = ShapeDoors[room.Room.Shape];
- for (var i = 0; i < exits.Length; i++)
- {
- if (exits[i] == default(Point))
- continue;
- var dstP = State.Pos.Add(exits[i]);
- if (!InBounds(dstP))
- continue;
- if (visited.Contains(dstP))
- continue;
- var dstRoom = State.GridState[dstP.Y][dstP.X];
- if (dstRoom.Revealed && dstRoom.Room != null && !IsPossible(dstP, visited))
- return false;
- }
- return true;
- }
- Point ChooseNextRoom()
- {
- var exits = ShapeDoors[State.CurrentRoom.Shape];
- for (var i = 0; i < exits.Length; i++)
- {
- exitRooms[i] = null;
- if (exits[i] == default(Point))
- continue;
- var dstP = State.Pos.Add(exits[i]);
- if (!InBounds(dstP))
- continue;
- var dstRoom = State.GridState[dstP.Y][dstP.X];
- if (dstRoom.Visited || dstRoom.Room == null)
- continue;
- if (dstRoom.Room.RoomType == RoomType.ROOM_BOSS)
- return dstP;
- if (dstRoom.Room.RoomType != RoomType.ROOM_DEFAULT)
- continue;
- if (!IsPossible(dstP, new HashSet<Point>()))
- {
- Func<RoomState, string> roomToChar = (room) =>
- {
- if (room == null || room.Room == null)
- return "O";
- return room.Visited ? "1" : "2";
- };
- for (var y = 0; y < 13; y++)
- {
- var line = string.Join("", Enumerable.Range(0, 13).Select(k => roomToChar(this.GridState[y][k])));
- Console.WriteLine(line);
- }
- IsPossible(dstP, new HashSet<Point>());
- continue;
- }
- exitRooms[i] = dstRoom;
- }
- Array.Sort(exitRooms, (l, r) =>
- {
- if (l == null && r != null)
- return 1;
- if (r == null && l != null)
- return -1;
- if (l == null && r == null)
- return 0;
- return ShapeWeights[l.Room.Shape].CompareTo(ShapeWeights[r.Room.Shape]);
- });
- return exitRooms[0] != null && exitRooms[0].Room != null ? new Point(exitRooms[0].Room.RoomX, exitRooms[0].Room.RoomY) : new Point(-1,-1);
- }
- public override bool Think()
- {
- GridState[State.Pos.Y][State.Pos.X].Visited = true;
- RevealRooms();
- var nextRoomPos = ChooseNextRoom();
- if (nextRoomPos.X == -1 && nextRoomPos.Y == -1)
- {
- if (Visited.Count < 1)
- {
- Func<RoomState, string> roomToChar = (room) =>
- {
- if (room == null || room.Room == null)
- return "O";
- return room.Visited ? "1" : "2";
- };
- for (var y = 0; y < 13; y++)
- {
- var line = string.Join("", Enumerable.Range(0, 13).Select(k => roomToChar(this.GridState[y][k])));
- Console.WriteLine(line);
- }
- throw new Exception("Ran out of choices before finding the boss room");
- }
- State.Pos = Visited.Pop();
- return true;
- }
- RoomsVisited++;
- var nextRoom = Grid[nextRoomPos.Y][nextRoomPos.X];
- var adjNextRoomPos = new Point(nextRoom.RoomX, nextRoom.RoomY);
- Visited.Push(State.Pos);
- State.Pos = adjNextRoomPos;
- if (State.CurrentRoom.RoomType == RoomType.ROOM_BOSS)
- return false;
- return true;
- }
- }
- public class Bot2 : Bot
- {
- Stack<Point> Visited = new Stack<System.Drawing.Point>();
- public int RoomsVisited;
- static RoomState[] exitRooms = new RoomState[8];
- #region weights
- static Dictionary<RoomShape, float> ShapeWeights = new Dictionary<UserQuery.RoomShape, float>
- {
- {RoomShape.ROOMSHAPE_1x1, 1},
- {RoomShape.ROOMSHAPE_1x2, 1.5f},
- {RoomShape.ROOMSHAPE_2x1, 1.5f},
- {RoomShape.ROOMSHAPE_2x2, 2},
- {RoomShape.ROOMSHAPE_IH, 1f},
- {RoomShape.ROOMSHAPE_IIH, 1.5f},
- {RoomShape.ROOMSHAPE_IIV, 1.5f},
- {RoomShape.ROOMSHAPE_IV, 1f},
- {RoomShape.ROOMSHAPE_LBL, 1.75f},
- {RoomShape.ROOMSHAPE_LBR, 1.75f},
- {RoomShape.ROOMSHAPE_LTL, 1.75f},
- {RoomShape.ROOMSHAPE_LTR, 1.75f},
- };
- #endregion
- Point ChooseNextRoom()
- {
- var exits = ShapeDoors[State.CurrentRoom.Shape];
- for (var i = 0; i < exits.Length; i++)
- {
- exitRooms[i] = null;
- if (exits[i] == default(Point))
- continue;
- var dstP = State.Pos.Add(exits[i]);
- if (!InBounds(dstP))
- continue;
- var dstRoom = State.GridState[dstP.Y][dstP.X];
- if (dstRoom.Visited || dstRoom.Room == null)
- continue;
- if (dstRoom.Room.RoomType != RoomType.ROOM_DEFAULT && dstRoom.Room.RoomType != RoomType.ROOM_BOSS)
- continue;
- exitRooms[i] = dstRoom;
- }
- Array.Sort(exitRooms, (l, r) =>
- {
- if (l == null && r != null)
- return 1;
- if (r == null && l != null)
- return -1;
- if (l == null && r == null)
- return 0;
- if (l.Room == null && r.Room != null)
- return 1;
- if (r.Room == null && l.Room != null)
- return -1;
- return -ShapeWeights[l.Room.Shape].CompareTo(ShapeWeights[r.Room.Shape]);
- });
- return exitRooms[0] != null && exitRooms[0].Room != null ? new Point(exitRooms[0].Room.RoomX, exitRooms[0].Room.RoomY) : new Point(-1, -1);
- }
- public override bool Think()
- {
- GridState[State.Pos.Y][State.Pos.X].Visited = true;
- var nextRoomPos = ChooseNextRoom();
- if (nextRoomPos.X == -1 && nextRoomPos.Y == -1)
- {
- if (Visited.Count < 1)
- throw new Exception("Ran out of choices before finding the boss room");
- State.Pos = Visited.Pop();
- return true;
- }
- RoomsVisited++;
- var nextRoom = Grid[nextRoomPos.Y][nextRoomPos.X];
- var adjNextRoomPos = new Point(nextRoom.RoomX, nextRoom.RoomY);
- Visited.Push(State.Pos);
- State.Pos = adjNextRoomPos;
- if (State.CurrentRoom.RoomType == RoomType.ROOM_BOSS)
- return false;
- return true;
- }
- }
- public static class PointExt
- {
- public static Point Add(this Point l, Point r)
- {
- return new Point(l.X+r.X, l.Y + r.Y);
- }
- }
- public class RoomDescriptor
- {
- public RoomType RoomType;
- public int RoomId; //variant
- public int RoomSubType;
- public RoomShape RoomShape;
- }
- public class RoomsProvider
- {
- public Dictionary<int, Dictionary<Tuple<RoomType, int>, RoomDescriptor>> StageRooms;
- public void Load(string path)
- {
- var xmlFiles = new DirectoryInfo(path).GetFiles("*.xml");
- StageRooms = new Dictionary<int, Dictionary<Tuple<RoomType, int>, RoomDescriptor>>();
- for (var i = 0; i < xmlFiles.Length; i++)
- {
- var stageIdx = int.Parse(Regex.Match(xmlFiles[i].Name, "^(\\d\\d)").Groups[1].Value);
- var doc = XDocument.Load(xmlFiles[i].FullName);
- var xmlRooms = doc.XPathSelectElements("//rooms/room").ToList();
- var rooms = new Dictionary<Tuple<RoomType, int>, RoomDescriptor>();
- for (var j = 0; j < xmlRooms.Count; j++)
- {
- var id = xmlRooms[j].Get<int>("variant");
- var type = (RoomType)xmlRooms[j].Get<int>("type");
- rooms[Tuple.Create(type, id)] = new RoomDescriptor
- {
- RoomType = type,
- RoomId = id,
- RoomSubType = xmlRooms[j].Get<int>("subtype"),
- RoomShape = (RoomShape)xmlRooms[j].Get<int>("shape")
- };
- }
- StageRooms[stageIdx] = rooms;
- }
- StageRooms[3] = StageRooms[1];
- StageRooms[6] = StageRooms[4];
- StageRooms[9] = StageRooms[7];
- StageRooms[12] = StageRooms[10];
- }
- }
- public class LayoutReader
- {
- Stream stream;
- RoomsProvider RoomsProv;
- public LayoutReader(Stream s, RoomsProvider roomsProv)
- {
- stream = s;
- RoomsProv = roomsProv;
- }
- public StageBlock Read()
- {
- if (stream.Position >= stream.Length)
- return null;
- var stages = new Stage[14];
- var seed = stream.ReadUInt32();
- for (var i = 0; i < 14; i++)
- {
- var stageId = stream.ReadInt8();
- var stageType = stream.ReadInt8();
- var roomCount = stream.ReadInt8();
- var gridCount = stream.ReadInt8();
- var grid = new Room[13][];
- for (var j = 0; j < grid.Length; j++)
- grid[j] = new Room[13];
- var seedStr = SeedToString(seed);
- var rooms = new Room[roomCount];
- for (var j = 0; j < gridCount; j++)
- {
- var sRoom = Room.ReadRoom(stream, RoomsProv);
- var room = rooms[sRoom.RoomOffset] ?? sRoom; //Have all of the grid parts of a room point to the same reference.
- grid[sRoom.RoomY][sRoom.RoomX] = room;
- rooms[room.RoomOffset] = room;
- }
- var iAmEror = Room.ReadNonGridRoom(stream, RoomsProv);
- var crawlSpace = Room.ReadNonGridRoom(stream, RoomsProv);
- var blackMarket = Room.ReadNonGridRoom(stream, RoomsProv);
- Room bossRush = null;
- if (stageId == 6)
- bossRush = Room.ReadNonGridRoom(stream, RoomsProv);
- stages[i] = new Stage(stageId, stageType, grid, rooms);
- }
- return new StageBlock { Seed = seed, Stages = stages };
- }
- }
- public class Room
- {
- public int StageIndex;
- public int RoomOffset;
- public int RoomX;
- public int RoomY;
- public RoomType RoomType;
- public int RoomSubType;
- public int RoomId;
- public RoomShape Shape;
- public static Room ReadRoom(Stream s, RoomsProvider prov)
- {
- var r = new Room
- {
- RoomOffset = s.ReadInt8(),
- RoomX = s.ReadInt8(),
- RoomY = s.ReadInt8(),
- StageIndex = s.ReadInt8(),
- RoomType = (RoomType)s.ReadInt8(),
- RoomSubType = s.ReadInt8(),
- RoomId = s.ReadInt16(),
- };
- r.Shape = prov.StageRooms[r.StageIndex][Tuple.Create(r.RoomType, r.RoomId)].RoomShape;
- return r;
- }
- public static Room ReadNonGridRoom(Stream s, RoomsProvider prov)
- {
- var r = new Room
- {
- RoomOffset = -1,
- RoomX = -1,
- RoomY = -1,
- StageIndex = s.ReadInt8(),
- RoomType = (RoomType)s.ReadInt8(),
- RoomSubType = s.ReadInt8(),
- RoomId = s.ReadInt16(),
- };
- r.Shape = prov.StageRooms[r.StageIndex][Tuple.Create(r.RoomType, r.RoomId)].RoomShape;
- return r;
- }
- }
- public enum FloorType
- {
- Special = 0,
- Basement = 1,
- Cellar = 2,
- BurningBasement = 3,
- Caves = 4,
- Catacombs = 5,
- FloodedCaves = 6,
- Depths = 7,
- Necropolis = 8,
- DankDepths = 9,
- Womb = 10,
- Utero = 11,
- ScarredWomb = 12,
- BlueWomb = 13,
- Sheol = 14,
- Cathedral = 15,
- DarkRoom = 16,
- Chest = 17,
- }
- public enum RoomType
- {
- ROOM_NULL = 0,
- ROOM_DEFAULT = 1,
- ROOM_SHOP = 2,
- ROOM_ERROR = 3,
- ROOM_TREASURE = 4,
- ROOM_BOSS = 5,
- ROOM_MINIBOSS = 6,
- ROOM_SECRET = 7,
- ROOM_SUPERSECRET = 8,
- ROOM_ARCADE = 9,
- ROOM_CURSE = 10,
- ROOM_CHALLENGE = 11,
- ROOM_LIBRARY = 12,
- ROOM_SACRIFICE = 13,
- ROOM_DEVIL = 14,
- ROOM_ANGEL = 15,
- ROOM_DUNGEON = 16,
- ROOM_BOSSRUSH = 17,
- ROOM_ISAACS = 18,
- ROOM_BARREN = 19,
- ROOM_CHEST = 20,
- ROOM_DICE = 21,
- ROOM_BLACK_MARKET = 22,
- ROOM_GREED_EXIT = 23,
- NUM_ROOMTYPES = 24
- }
- public enum RoomShape
- {
- ROOMSHAPE_NULL = 0,
- ROOMSHAPE_1x1 = 1,
- ROOMSHAPE_IH = 2,
- ROOMSHAPE_IV = 3,
- ROOMSHAPE_1x2 = 4,
- ROOMSHAPE_IIV = 5,
- ROOMSHAPE_2x1 = 6,
- ROOMSHAPE_IIH = 7,
- ROOMSHAPE_2x2 = 8,
- ROOMSHAPE_LTL = 9,
- ROOMSHAPE_LTR = 10,
- ROOMSHAPE_LBL = 11,
- ROOMSHAPE_LBR = 12,
- NUM_ROOMSHAPES = 13
- }
- public class Stage
- {
- public int StageId;
- public int StageType;
- public Room[][] RoomGrid;
- public Room[] Rooms;
- public Stage(int stageId, int stageType, Room[][] grid, Room[] rooms)
- {
- StageId = stageId;
- StageType = stageType;
- RoomGrid = grid;
- Rooms = rooms;
- }
- }
- public class StageBlock
- {
- public uint Seed;
- public Stage[] Stages;
- }
- enum Direction : int
- {
- None = 0,
- North = 1,
- East = 2,
- South = 4,
- West = 8,
- NorthEast = North | East,
- NorthWest = North | West,
- SouthEast = South | East,
- SouthWest = South | West,
- }
- // Define other methods and classes here
- static string SeedToString(uint num)
- {
- const string chars = "ABCDEFGHJKLMNPQRSTWXYZ01234V6789";
- byte x = 0;
- var tnum = num;
- while (tnum != 0)
- {
- x += ((byte)tnum);
- x += (byte)(x + (x >> 7));
- tnum >>= 5;
- }
- num ^= 0x0FEF7FFD;
- tnum = (num) << 8 | x;
- var ret = new char[8];
- for (int i = 0; i < 6; i++)
- {
- ret[i] = chars[(int)(num >> (27 - (i * 5)) & 0x1F)];
- }
- ret[6] = chars[(int)(tnum >> 5 & 0x1F)];
- ret[7] = chars[(int)(tnum & 0x1F)];
- return new string(ret);
- }
- class Rng
- {
- public uint seed;
- public int shift1;
- public int shift2;
- public int shift3;
- public uint next()
- {
- var num = seed;
- num ^= num >> shift1;
- num ^= num << shift2;
- num ^= num >> shift3;
- seed = num;
- return num;
- }
- };
Advertisement
Add Comment
Please, Sign In to add comment