Vice City: Multiplayer

Server Development => Scripting and Server Management => Snippet Showroom => Topic started by: Milos on Mar 11, 2019, 04:20 PM

Title: Top Killers System
Post by: Milos on Mar 11, 2019, 04:20 PM

And I created a Top Killer system without using database every time it is called:

Create a table:
Accounts <- {}; /* Table where accounts will be */
Functions:
/* Let's say we are loading the accounts from the database */
function loadAccounts() {
    //9 "accounts"
    Accounts.rawset(1, {Name = "Player1", Kills = rand() % 1000});
    Accounts.rawset(2, {Name = "Player2", Kills = rand() % 1000});
    Accounts.rawset(3, {Name = "Player3", Kills = rand() % 1000});
    Accounts.rawset(4, {Name = "Player4", Kills = rand() % 1000});
    Accounts.rawset(5, {Name = "Player5", Kills = rand() % 1000});
    Accounts.rawset(6, {Name = "Player6", Kills = rand() % 1000});
    Accounts.rawset(7, {Name = "Player7", Kills = rand() % 1000});
    Accounts.rawset(8, {Name = "Player8", Kills = rand() % 1000});
    Accounts.rawset(9, {Name = "Player9", Kills = rand() % 1000});
/* NOTE: You will have to adapt this function to load all the accounts of your database. */
}

function topKills() {
    /*Here, we will temporarily clone the original table, because we will
      have to delete some data (and we do not want this to happen in the main table)*/
    local backup_Accounts = clone Accounts;
 
    local limit = 5, tmp = "";
    while (limit) {
        local topScore = 0, index = 0;
        foreach (i, v in backup_Accounts)
        {
            if (backup_Accounts[i]["Kills"] > topScore) {
                topScore = backup_Accounts[i]["Kills"];
                index = i;
            }
        }
        if (index) tmp = tmp + backup_Accounts[index]["Name"] + " - " + backup_Accounts[index]["Kills"] + ", ";
        backup_Accounts.rawdelete(index);
        limit --;
    }
    return tmp != "" ? tmp.slice(0, tmp.len() - 2) : "No top killers";
}
 
function getAccountID(str) {
    foreach (i, v in Accounts) {
        if (Accounts[i]["Name"].tolower() == str.tolower()) {
            return i;
            break;
        }
    }
    return 0;
}

Server Events:
function onScriptLoad() {
    loadAccounts();
    print(topKills());
}
 
function onPlayerKill(killer, player, reason, bodypart) {
    /* Do not forget to update the amount of kills when the player scores */
    local i = getAccountID(killer.Name);
    if (i) Accounts[i]["Kills"] ++;
}

Result:
(https://i.imgur.com/goIivwJl.png)

My server:
(https://i.imgur.com/Ih4D9rq.png)

* I do not know why it always starts with the same values, even using the rand(), but you can change each kill in the loadAccounts function to confirm the script's operation (Someone explains to me)

Title: Re: Top Killers System
Post by: dracc on Mar 12, 2019, 12:08 AM
You're using a table anyway, why not just use player.Name as key and kills as value and then populate a five slot array accordingly in your topKills() function? Would save a lot of lookup-complexity and lines of code.
Also, what happens when you don't have five players in your Accounts table? Should result in some nasty errors as you go out-of-bounds.
Title: Re: Top Killers System
Post by: Milos on Mar 12, 2019, 05:07 AM
Quote from: dracc on Mar 12, 2019, 12:08 AMYou're using a table anyway, why not just use player.Name as key and kills as value and then populate a five slot array accordingly in your topKills() function? Would save a lot of lookup-complexity and lines of code.
Also, what happens when you don't have five players in your Accounts table? Should result in some nasty errors as you go out-of-bounds.

player.Name? hhhhh How am I going to use this if I'm checking all the accounts and not just the online players?
TopKillers!!!!
BEST 5 KILLS FROM ALL SERVER ACCOUNTS
Title: Re: Top Killers System
Post by: dracc on Mar 12, 2019, 07:46 AM
Quote from: Pau Grosso on Mar 12, 2019, 05:07 AM
Quote from: dracc on Mar 12, 2019, 12:08 AMYou're using a table anyway, why not just use player.Name as key and kills as value and then populate a five slot array accordingly in your topKills() function? Would save a lot of lookup-complexity and lines of code.
Also, what happens when you don't have five players in your Accounts table? Should result in some nasty errors as you go out-of-bounds.

player.Name? hhhhh How am I going to use this if I'm checking all the accounts and not just the online players?
TopKillers!!!!
BEST 5 KILLS FROM ALL SERVER ACCOUNTS

How often are you planning on attributing kills to players who are not online? :o
It's quite possible you have many parts to this script which you haven't shown us - but there's no way for us others to know that, is there?

Accounts <- {};

function loadAccounts() {
  // Fetch all accounts into the Accounts table.
  // Pseudo-code follows:
  // db <- ConnectSQL("SQLite.db");
  // QuerySQL(db, "CREATE TABLE IF NOT EXISTS Accounts(name TEXT PRIMARY KEY, kills INTEGER);");
  // local q = QuerySQL(db, "SELECT name, kills FROM Accounts");
  // if (q) {
  //   do {
  //     Accounts[SQLGetColumnData(q, 0)] <- SQLGetColumnData(q, 1);
  //   } while (GetSQLNextRow(q));
  // }
}

function onScriptLoad() {
  loadAccounts();
  print(topKills());
}

function onPlayerKill(killer, player, reason, bodypart) {
  if (killer.Name in Accounts) {
    Accounts[killer.Name]++;
  }
}

function sortByKills(lhs, rhs) {
  if (lhs[1] < rhs[1]) {
    return 1;
  } else if (lhs[1] > rhs[1]) {
    return -1;
  } else {
    return 0;
  }
}

function topKills() {
  local iterationSize = (Accounts.len() >= 5 ? 5 : Accounts.len());
  if (iterationSize == 0) {
    return "No top killers.";
  }
  local killerArray = [];
  foreach (Name, Kills in Accounts) {
    killerArray.push([Name, Kills]);
  }
  killerArray.sort(sortByKills);
  local killerToplist = killerArray[0][0] + " - " + killerArray[0][1];
  local i;
  for (i = 1; i < iterationSize; ++i) {
    killerToplist += ", " + killerArray[i][0] + " - " + killerArray[i][1];
  }
  return killerToplist;
}
Title: Re: Top Killers System
Post by: Milos on Mar 12, 2019, 01:46 PM
I do not understand how the database structure of the various scripters here, so I used this:
/* Let's say we are loading the accounts from the database */
function loadAccounts() {
    Accounts.rawset(1, {Name = "Player1", Kills = rand() % 1000});
    Accounts.rawset(2, {Name = "Player2", Kills = rand() % 1000});
    Accounts.rawset(3, {Name = "Player3", Kills = rand() % 1000});
    Accounts.rawset(4, {Name = "Player4", Kills = rand() % 1000});
    Accounts.rawset(5, {Name = "Player5", Kills = rand() % 1000});
    Accounts.rawset(6, {Name = "Player6", Kills = rand() % 1000});
    Accounts.rawset(7, {Name = "Player7", Kills = rand() % 1000});
    Accounts.rawset(8, {Name = "Player8", Kills = rand() % 1000});
    Accounts.rawset(9, {Name = "Player9", Kills = rand() % 1000});
}
I'll put in original post.
Title: Re: Top Killers System
Post by: UrbanY on Mar 12, 2019, 03:12 PM
function onScriptLoad()
{
NewTimer( "TopKillers", 60000, 0 );
}
function TopKillers()

local
query = "SELECT Name, Mato FROM Accounts ORDER BY Name DESC LIMIT 5", //Top 5
q,
Name1, Name2, Name3, Name4, Name5,
Top1, Top2, Top3, Top4, Top5, i = 1; 
q = QuerySQL( db, query );
while( GetSQLColumnData( q, 0 ) )
{
switch(i)
{
case 1:
Name1 = GetSQLColumnData( q, 0 );
Top1 = GetSQLColumnData( q, 1 );
break;
case 2:
Name2 = GetSQLColumnData( q, 0 );
Top2 = GetSQLColumnData( q, 1 );
break;
case 3:
Name3 = GetSQLColumnData( q, 0 );
Top3 = GetSQLColumnData( q, 1 );
break; 
case 4:
Name4 = GetSQLColumnData( q, 0 );
Top4 = GetSQLColumnData( q, 1 );
break;
case 5:
Name5 = GetSQLColumnData( q, 0 ); 
Top5 = GetSQLColumnData( q, 1 );
break; 
}
GetSQLNextRow( q );
i++;
}
FreeSQLQuery(q);
Message("[#00ffff]Top 5 Matadores | Killers[#000000]: [#00bfff]" + Name1 + " [#ffffff]: [#00ff00]" + Top1 + ", [#00bfff]" + Name2 + " [#ffffff]: [#00ff00]" + Top2 + ", [#00bfff]" + Name3 + " [#ffffff]: [#00ff00]" + Top3 + ", [#00bfff]" + Name4 + " [#ffffff]: [#00ff00]" + Top4 + ", [#00bfff]" + Name5 + " [#ffffff]: [#00ff00]" + Top5 + "");
}
Title: Re: Top Killers System
Post by: Milos on Mar 12, 2019, 03:32 PM
Quote from: UrbanY on Mar 12, 2019, 03:12 PMfunction onScriptLoad()
{
NewTimer( "TopKillers", 60000, 0 );
}
function TopKillers()

local
query = "SELECT Name, Mato FROM Accounts ORDER BY Name DESC LIMIT 5", //Top 5
q,
Name1, Name2, Name3, Name4, Name5,
Top1, Top2, Top3, Top4, Top5, i = 1; 
q = QuerySQL( db, query );
while( GetSQLColumnData( q, 0 ) )
{
switch(i)
{
case 1:
Name1 = GetSQLColumnData( q, 0 );
Top1 = GetSQLColumnData( q, 1 );
break;
case 2:
Name2 = GetSQLColumnData( q, 0 );
Top2 = GetSQLColumnData( q, 1 );
break;
case 3:
Name3 = GetSQLColumnData( q, 0 );
Top3 = GetSQLColumnData( q, 1 );
break; 
case 4:
Name4 = GetSQLColumnData( q, 0 );
Top4 = GetSQLColumnData( q, 1 );
break;
case 5:
Name5 = GetSQLColumnData( q, 0 ); 
Top5 = GetSQLColumnData( q, 1 );
break; 
}
GetSQLNextRow( q );
i++;
}
FreeSQLQuery(q);
Message("[#00ffff]Top 5 Matadores | Killers[#000000]: [#00bfff]" + Name1 + " [#ffffff]: [#00ff00]" + Top1 + ", [#00bfff]" + Name2 + " [#ffffff]: [#00ff00]" + Top2 + ", [#00bfff]" + Name3 + " [#ffffff]: [#00ff00]" + Top3 + ", [#00bfff]" + Name4 + " [#ffffff]: [#00ff00]" + Top4 + ", [#00bfff]" + Name5 + " [#ffffff]: [#00ff00]" + Top5 + "");
}
Quote from: Pau Grosso on Mar 11, 2019, 04:20 PMAnd I created a Top Killer system without using database every time it is called
Title: Re: Top Killers System
Post by: dracc on Mar 12, 2019, 06:04 PM
Quote from: UrbanY on Mar 12, 2019, 03:12 PM...

Wow, that must be the ugliest solution possible for a toplist. Especially since you sort by name instead of score. ????
Title: Re: Top Killers System
Post by: UrbanY on Mar 12, 2019, 11:04 PM
Quote from: dracc on Mar 12, 2019, 06:04 PM
Quote from: UrbanY on Mar 12, 2019, 03:12 PM...

Wow, that must be the ugliest solution possible for a toplist. Especially since you sort by name instead of score. ????
I just came to help not to read the idiocies you want to say about my script.
Title: Re: Top Killers System
Post by: dracc on Mar 13, 2019, 04:46 AM
Quote from: UrbanY on Mar 12, 2019, 11:04 PM
Quote from: dracc on Mar 12, 2019, 06:04 PM
Quote from: UrbanY on Mar 12, 2019, 03:12 PM...

Wow, that must be the ugliest solution possible for a toplist. Especially since you sort by name instead of score. ????
I just came to help not to read the idiocies you want to say about my script.
"Help" by writing shitty code that doesn't even work when two working examples have already been shown and yours doesn't (even if it didn't have the typo) solve the problem at hand? Wow, great help.