r6058 - in trunk/data/qcsrc: common server
DONOTREPLY at icculus.org
DONOTREPLY at icculus.org
Fri Mar 6 06:07:46 EST 2009
Author: div0
Date: 2009-03-06 06:07:43 -0500 (Fri, 06 Mar 2009)
New Revision: 6058
Modified:
trunk/data/qcsrc/common/gamecommand.qc
trunk/data/qcsrc/common/util.qc
trunk/data/qcsrc/common/util.qh
trunk/data/qcsrc/server/g_world.qc
Log:
better maplist shffle method
Modified: trunk/data/qcsrc/common/gamecommand.qc
===================================================================
--- trunk/data/qcsrc/common/gamecommand.qc 2009-03-06 10:57:01 UTC (rev 6057)
+++ trunk/data/qcsrc/common/gamecommand.qc 2009-03-06 11:07:43 UTC (rev 6058)
@@ -116,28 +116,12 @@
}
else if(argv(1) == "shuffle" && argc == 2)
{
- // TODO make this work for huge lists
- s = cvar_string("g_maplist");
- for(i = 1; i < (n = tokenizebyseparator(s, " ")); ++i)
- {
- // swap i-th item at a random position from 0 to i
- // proof for even distribution:
- // n = 1: obvious
- // n -> n+1:
- // item n+1 gets at any position with chance 1/(n+1)
- // all others will get their 1/n chance reduced by factor n/(n+1)
- // to be on place n+1, their chance will be 1/(n+1)
- // 1/n * n/(n+1) = 1/(n+1)
- // q.e.d.
- f = floor(random() * (i + 1)); // 0 to i
- if(f == i)
- continue; // no change
-
- s2 = "";
- for(j = 0; j < n; ++j)
- s2 = strcat(s2, " ", argv((j == i) ? f : (j == f) ? i : j));
- s = substring(s2, 1, strlen(s2) - 1);
- }
+ n = tokenizebyseparator(cvar_string("g_maplist"), " ");
+ shufflearray_build(n);
+ s2 = "";
+ for(i = 0; i < n; ++i)
+ s2 = strcat(s2, " ", argv(shufflearray[i]));
+ s = substring(s2, 1, strlen(s2) - 1);
cvar_set("g_maplist", s);
return TRUE;
}
Modified: trunk/data/qcsrc/common/util.qc
===================================================================
--- trunk/data/qcsrc/common/util.qc 2009-03-06 10:57:01 UTC (rev 6057)
+++ trunk/data/qcsrc/common/util.qc 2009-03-06 11:07:43 UTC (rev 6058)
@@ -1498,3 +1498,43 @@
}
return 1;
}
+
+void shuffle(float n, shuffle_swapfunc_t swap)
+{
+ float i, j;
+ for(i = 1; i < n; ++i)
+ {
+ // swap i-th item at a random position from 0 to i
+ // proof for even distribution:
+ // n = 1: obvious
+ // n -> n+1:
+ // item n+1 gets at any position with chance 1/(n+1)
+ // all others will get their 1/n chance reduced by factor n/(n+1)
+ // to be on place n+1, their chance will be 1/(n+1)
+ // 1/n * n/(n+1) = 1/(n+1)
+ // q.e.d.
+ j = floor(random() * (i + 1));
+ if(j != i)
+ swap(i, j);
+ }
+}
+
+void shufflearray_init(float n)
+{
+ float i;
+ for(i = 0; i < n; ++i)
+ shufflearray[i] = i;
+}
+void shufflearray_swap(float i, float j)
+{
+ float h;
+ h = shufflearray[i];
+ shufflearray[i] = shufflearray[j];
+ shufflearray[j] = h;
+}
+
+void shufflearray_build(float n)
+{
+ shufflearray_init(n);
+ shuffle(n, shufflearray_swap);
+}
Modified: trunk/data/qcsrc/common/util.qh
===================================================================
--- trunk/data/qcsrc/common/util.qh 2009-03-06 10:57:01 UTC (rev 6057)
+++ trunk/data/qcsrc/common/util.qh 2009-03-06 11:07:43 UTC (rev 6058)
@@ -152,3 +152,9 @@
string getWrappedLine(float w, textLengthUpToWidth_widthFunction_t tw);
float isGametypeInFilter(float gt, float tp, string pattern);
+
+typedef void(float i1, float i2) shuffle_swapfunc_t;
+void shuffle(float n, shuffle_swapfunc_t swap);
+
+float shufflearray[1024];
+void shufflearray_build(float n);
Modified: trunk/data/qcsrc/server/g_world.qc
===================================================================
--- trunk/data/qcsrc/server/g_world.qc 2009-03-06 10:57:01 UTC (rev 6057)
+++ trunk/data/qcsrc/server/g_world.qc 2009-03-06 11:07:43 UTC (rev 6058)
@@ -1625,37 +1625,16 @@
void ShuffleMaplist()
{
- string result;
- float start;
- float litems;
- float selected;
- float i;
+ float n, i;
+ string s, s2;
- result = cvar_string("g_maplist");
- litems = tokenizebyseparator(result, " ");
-
- for(start = 0; start < litems - 1; ++start)
- {
- result = "";
-
- // select a random item
- selected = floor(random() * (litems - start) + start);
-
- // shift this item to the place start
- for(i = 0; i < start; ++i)
- result = strcat(result, " ", argv(i));
- result = strcat(result, " ", argv(selected));
- for(i = start; i < litems; ++i)
- if(i != selected)
- result = strcat(result, " ", argv(i));
- result = substring(result, 1, strlen(result) - 1);
-
- litems = tokenizebyseparator(result, " ");
-
- //dprint(result, "\n");
- }
-
- cvar_set("g_maplist", result);
+ n = tokenizebyseparator(cvar_string("g_maplist"), " ");
+ shufflearray_build(n);
+ s2 = "";
+ for(i = 0; i < n; ++i)
+ s2 = strcat(s2, " ", argv(shufflearray[i]));
+ s = substring(s2, 1, strlen(s2) - 1);
+ cvar_set("g_maplist", s);
}
float leaderfrags;
More information about the nexuiz-commits
mailing list