Making the level calculator more efficient

This commit is contained in:
Runebaas 2017-10-25 00:58:59 +02:00
parent ac73a8e6f9
commit 1f48d0387b
No known key found for this signature in database
GPG key ID: 2677AF508D0300D6
4 changed files with 59 additions and 33 deletions

View file

@ -10,11 +10,15 @@ namespace Geekbot.net.Commands
{ {
public class GuildInfo : ModuleBase public class GuildInfo : ModuleBase
{ {
private readonly IDatabase redis; private readonly IDatabase _redis;
private readonly ILevelCalc _levelCalc;
private readonly IErrorHandler _errorHandler;
public GuildInfo(IDatabase redis) public GuildInfo(IDatabase redis, ILevelCalc levelCalc, IErrorHandler errorHandler)
{ {
this.redis = redis; _redis = redis;
_levelCalc = levelCalc;
_errorHandler = errorHandler;
} }
[Command("serverstats", RunMode = RunMode.Async)] [Command("serverstats", RunMode = RunMode.Async)]
@ -22,23 +26,30 @@ namespace Geekbot.net.Commands
[Summary("Show some info about the bot.")] [Summary("Show some info about the bot.")]
public async Task getInfo() public async Task getInfo()
{ {
var eb = new EmbedBuilder(); try
eb.WithAuthor(new EmbedAuthorBuilder() {
.WithIconUrl(Context.Guild.IconUrl) var eb = new EmbedBuilder();
.WithName(Context.Guild.Name)); eb.WithAuthor(new EmbedAuthorBuilder()
eb.WithColor(new Color(110, 204, 147)); .WithIconUrl(Context.Guild.IconUrl)
.WithName(Context.Guild.Name));
eb.WithColor(new Color(110, 204, 147));
var created = Context.Guild.CreatedAt; var created = Context.Guild.CreatedAt;
var age = Math.Floor((DateTime.Now - created).TotalDays); var age = Math.Floor((DateTime.Now - created).TotalDays);
var messages = redis.HashGet($"{Context.Guild.Id}:Messages", 0.ToString()); var messages = _redis.HashGet($"{Context.Guild.Id}:Messages", 0.ToString());
var level = LevelCalc.GetLevelAtExperience((int) messages); var level = _levelCalc.GetLevelAtExperience((int) messages);
eb.AddField("Server Age", $"{created.Day}/{created.Month}/{created.Year} ({age} days)"); eb.AddField("Server Age", $"{created.Day}/{created.Month}/{created.Year} ({age} days)");
eb.AddInlineField("Level", level) eb.AddInlineField("Level", level)
.AddInlineField("Messages", messages); .AddInlineField("Messages", messages);
await ReplyAsync("", false, eb.Build()); await ReplyAsync("", false, eb.Build());
}
catch (Exception e)
{
_errorHandler.HandleCommandException(e, Context);
}
} }
public static string FirstCharToUpper(string input) public static string FirstCharToUpper(string input)

View file

@ -11,11 +11,13 @@ namespace Geekbot.net.Commands
{ {
private readonly IDatabase _redis; private readonly IDatabase _redis;
private readonly IErrorHandler _errorHandler; private readonly IErrorHandler _errorHandler;
private readonly ILevelCalc _levelCalc;
public Stats(IDatabase redis, IErrorHandler errorHandler) public Stats(IDatabase redis, IErrorHandler errorHandler, ILevelCalc levelCalc)
{ {
_redis = redis; _redis = redis;
_errorHandler = errorHandler; _errorHandler = errorHandler;
_levelCalc = levelCalc;
} }
[Command("stats", RunMode = RunMode.Async)] [Command("stats", RunMode = RunMode.Async)]
@ -34,7 +36,7 @@ namespace Geekbot.net.Commands
var messages = (int) _redis.HashGet($"{Context.Guild.Id}:Messages", userInfo.Id.ToString()); var messages = (int) _redis.HashGet($"{Context.Guild.Id}:Messages", userInfo.Id.ToString());
var guildMessages = (int) _redis.HashGet($"{Context.Guild.Id}:Messages", 0.ToString()); var guildMessages = (int) _redis.HashGet($"{Context.Guild.Id}:Messages", 0.ToString());
var level = LevelCalc.GetLevelAtExperience(messages); var level = _levelCalc.GetLevelAtExperience(messages);
var percent = Math.Round((double) (100 * messages) / guildMessages, 2); var percent = Math.Round((double) (100 * messages) / guildMessages, 2);

View file

@ -1,27 +1,38 @@
using System; using System;
using System.Collections.Generic;
namespace Geekbot.net.Lib namespace Geekbot.net.Lib
{ {
internal class LevelCalc internal class LevelCalc : ILevelCalc
{ {
private static int GetExperienceAtLevel(int level) private int[] _levels;
{
double total = 0;
for (var i = 1; i < level; i++)
total += Math.Floor(i + 300 * Math.Pow(2, i / 7.0));
return (int) Math.Floor(total / 16); public LevelCalc()
{
var levels = new List<int>();
double total = 0;
for (var i = 1; i < 120; i++)
{
total += Math.Floor(i + 300 * Math.Pow(2, i / 7.0));
levels.Add((int) Math.Floor(total / 16));
}
_levels = levels.ToArray();
} }
public static int GetLevelAtExperience(int experience) public int GetLevelAtExperience(int experience)
{ {
int index; var returnVal = 1;
foreach (var level in _levels)
for (index = 0; index < 120; index++) {
if (GetExperienceAtLevel(index + 1) > experience) if (level > experience) break;
break; returnVal++;
}
return index; return returnVal;
} }
} }
public interface ILevelCalc
{
int GetLevelAtExperience(int experience);
}
} }

View file

@ -109,11 +109,13 @@ namespace Geekbot.net
var fortunes = new FortunesProvider(randomClient, logger); var fortunes = new FortunesProvider(randomClient, logger);
var mediaProvider = new MediaProvider(randomClient, logger); var mediaProvider = new MediaProvider(randomClient, logger);
var malClient = new MalClient(redis, logger); var malClient = new MalClient(redis, logger);
var levelCalc = new LevelCalc();
services.AddSingleton<IErrorHandler>(errorHandler); services.AddSingleton<IErrorHandler>(errorHandler);
services.AddSingleton(redis); services.AddSingleton(redis);
services.AddSingleton<ILogger>(logger); services.AddSingleton<ILogger>(logger);
services.AddSingleton<IUserRepository>(userRepository); services.AddSingleton<IUserRepository>(userRepository);
services.AddSingleton<ILevelCalc>(levelCalc);
services.AddSingleton(randomClient); services.AddSingleton(randomClient);
services.AddSingleton<IFortunesProvider>(fortunes); services.AddSingleton<IFortunesProvider>(fortunes);
services.AddSingleton<IMediaProvider>(mediaProvider); services.AddSingleton<IMediaProvider>(mediaProvider);