EDIT RemoveAt
- слабость в моей предыдущей версии. Это решение преодолевает это.
public static IEnumerable Shuffle(
this IEnumerable source,
Random generator = null)
{
if (generator == null)
{
generator = new Random();
}
var elements = source.ToArray();
for (var i = elements.Length - 1; i >= 0; i--)
{
var swapIndex = generator.Next(i + 1);
yield return elements[swapIndex];
elements[swapIndex] = elements[i];
}
}
Обратите внимание на необязательный параметр Random generator
, если реализация базовой фреймворка Random
не является потокобезопасной или криптографически достаточно сильной для ваших нужд, вы можете ввести свою реализацию в операция.
Вот идея, расширить IList в (надеюсь) эффективный путь.
public static IEnumerable Shuffle(this IList list)
{
var choices = Enumerable.Range(0, list.Count).ToList();
var rng = new Random();
for(int n = choices.Count; n > 1; n--)
{
int k = rng.Next(n);
yield return list[choices[k]];
choices.RemoveAt(k);
}
yield return list[choices[0]];
}
Два вопроса думать о:
Если у Вас есть небольшое количество столбцов кандидата, и данные не изменяются много, то Вы могли бы хотеть рассмотреть добавление постоянного индекса на любом или даже всем столбце кандидата.
"Богохульство!", я слышу. Большинство источников говорит Вам "никогда" не индексировать каждый столбец таблицы, но рекомендуемый базирован на универсальном предположении, что таблицы часто изменяются.
Вы будете расплачиваться в дополнительном устройстве хранения данных, а также хите производительности, когда данные изменятся.
Как маленький является маленьким и сколько много, и действительно ли компромисс стоит того? Нет никакого способа сказать монастырю, потому что "слишком медленный" обычно субъективное измерение.
Необходимо будет попробовать его, измерить размер индексов и затем эффекта, который они имеют в поисках. Необходимо будет сбалансировать затраты относительно увеличения удовлетворенности клиентов.
[Добавленный], О, еще одна вещь: временные индексы не только физически медленнее, чем сканирование таблицы, но и они уничтожили бы Ваш параллелизм. Переиндексация таблицы обычно (всегда?) требует полной блокировки таблицы, поэтому в действительности только один пользовательский поиск мог быть сделан за один раз.
Удачи.
Я не DBA, но я предположил бы, что создание индекса потребует сканирования таблицы так или иначе.
Если там не будут несколькими запросами на том столбце, я рекомендовал бы не создать индекс.
Лучше всего проверять объяснить планы/время выполнения относительно обоих путей, хотя!
Как все остальные сказали, это несомненно не было бы быстрее для добавления индекса, чем это должно будет сделать полное сканирование того столбца.
Однако я предложил бы отследить шаблон запроса и узнал бы, какой столбец (столбцы) ищутся большинство и добавляют индексы, по крайней мере, для них. Можно узнать, что 3-4 индекса ускоряют 90% запросов.
Добавление индекса требует сканирования таблицы, поэтому если Вы не можете добавить постоянный индекс, оно кажется, что единственное сканирование будет (немного) быстрее.
Нет, это не было бы более быстро. Что было бы более быстрым, состоит в том, чтобы просто добавить индекс и оставить его там!
Конечно, это не может быть практично для индексации каждого столбца, но с другой стороны это может. Как данные добавляются к таблице?
Это не было бы. Создание индекса более сложно, чем простое сканирование столбца, даже если вычислительная сложность является тем же.
Это сказало - сколько столбцов Вы имеете? Вы уверены, что не можете только создать индекс для каждого из них, если время запроса для единственной находки является слишком длинным?
Это зависит от сложности Вашего запроса. Если Вы получаете данные однажды, то выполнение сканирования таблицы быстрее. Однако, если Вы возвращаетесь к таблице несколько раз для сопутствующей информации в том же запросе, затем индекс быстрее.
Другая связанная стратегия состоит в том, чтобы сделать сканирование таблицы и поместить все данные во временную таблицу. Затем индекс ЭТО и затем можно сделать все последующие выборы, группировки, и как много других запросов на подмножестве индексируемых данных. Так как преимущество является тем поиском сопутствующей информации в связанных таблицах с помощью временной таблицы, НАМНОГО быстрее.
Однако пространство является дешевым в эти дни, таким образом, Вы были бы, вероятно, лучше всего обслужены путем исследования, как пользователи на самом деле ИСПОЛЬЗУЮТ систему и добавляющие индексы на тех частых столбцах. Я должен все же видеть, что пользователи используют ВСЕ поисковые параметры Все время.
Ваше решение не масштабируется, если Вы не добавите постоянный индекс к каждому столбцу со всеми столбцами, которые возвращаются в запросе в списке включенных столбцов (закрывающий индекс). Эти индексы будут очень большими, и вставляют и обновляют к той таблице, будет немного медленнее, но у Вас нет большой части выбора, если Вы позволяете пользователю произвольно выбирать поисковый столбец.
Сколько столбцы там? Как часто данные становятся обновленными? То, как быстро делают, вставляет и обновляет потребность работать? Существуют компромиссы, включенные, в зависимости от ответов на те вопросы. Сделайте много экспериментирования и тестирующий, таким образом, Вы знаете наверняка, как вещи будут работать.
Но к Вашему исходному вопросу, добавляя и отбрасывая индекс в целях единого запроса только выгодно, если Вы делаете больше чем один выбор во время запроса (например, выбор находится в подзапросе, который выполняется для каждой возвращенной строки).