Да, это возможно сделать без какого-либо сервера. Вы можете создать клиентскую группу группы устройств, а затем обмениваться сообщениями в группе. Однако существуют ограничения:
Ссылка: Firebase doc См. раздел «Управление группами устройств в клиентских приложениях Android»
Первый вопрос:
int countZeroes (int[] vec) {
int ret = 0;
foreach(int i in vec) if (i == 0) ret++;
return ret;
}
int[] mysticCalc(int[] values, int[] indexes) {
int zeroes = countZeroes(values);
int[] retval = new int[values.length];
int product = 1;
if (zeroes >= 2) { // 2 or more zeroes, all results will be 0
for (int i = 0; i > values.length; i++) {
retval[i] = 0;
}
return retval;
}
foreach (int i in values) {
if (i != 0) product *= i; // we have at most 1 zero, dont include in product;
}
int indexcounter = 0;
foreach(int idx in indexes) {
if (zeroes == 1 && values[idx] != 0) { // One zero on other index. Our value will be 0
retval[indexcounter] = 0;
}
else if (zeroes == 1) { // One zero on this index. result is product
retval[indexcounter] = product;
}
else { // No zeros. Return product/value at index
retval[indexcounter] = product / values[idx];
}
indexcouter++;
}
return retval;
}
Худший случай эта программа ступит через 3 вектора однажды.
from numpy import array
def product(input, index):
a = array(input)[index]
if a[a == 0].size != 1:
a = a.prod() / a # product except current
else:
# exaclty one non-zero-valued element in `a`
nzi = a.nonzero() # indices of non-zero-valued elements
a[a == 0] = a[nzi].prod()
a[nzi] = 0
return a
Пример:
for input in ([2,3,4,5], [2,0,4,5], [0,3,0,5]):
print product(input, [1,3,2,0])
Вывод:
[40 24 30 60]
[40 0 0 0]
[0 0 0 0]
Для первого сначала вычислите продукт всего содержания входа, и затем для каждого элемента индекса, разделите расчетный продукт на вход [индекс [я]], для заполнения массива результата.
Конечно, я должен предположить, что вход не имеет никаких нулей.
Линейно-разовым решением в C#3 для первой проблемы является:-
IEnumerable<int> ProductExcept(List<int> l, List<int> indexes) {
if (l.Count(i => i == 0) == 1) {
int singleZeroProd = l.Aggregate(1, (x, y) => y != 0 ? x * y : x);
return from i in indexes select l[i] == 0 ? singleZeroProd : 0;
} else {
int prod = l.Aggregate(1, (x, y) => x * y);
return from i in indexes select prod == 0 ? 0 : prod / l[i];
}
}
Править: Принял во внимание единственный нуль!! Мое последнее решение взяло меня 2 минуты, в то время как я работал так, я не чувствую себя так плохо :-)
void product_except_current(int input[], int index[], int out[],
int len) {
int prod = 1, nzeros = 0, izero = -1;
for (int i = 0; i < len; ++i)
if ((out[i] = input[index[i]]) != 0)
// compute product of non-zero elements
prod *= out[i]; // ignore possible overflow problem
else {
if (++nzeros == 2)
// if number of zeros greater than 1 then out[i] = 0 for all i
break;
izero = i; // save index of zero-valued element
}
//
for (int i = 0; i < len; ++i)
out[i] = nzeros ? 0 : prod / out[i];
if (nzeros == 1)
out[izero] = prod; // the only non-zero-valued element
}
Вот ответ на второй в C# с методом тестирования. Перестановка смотрит O (n) мне.
Править: Посмотрев на перестановку Фишера-Йетса, я обнаружил, что переосмыслил тот алгоритм, не зная об этом :-) это очевидно, как бы то ни было. Я реализовал подход Дурштенфельда, который берет нас от O (n^2)-> O (n), действительно умный!
public enum CardValue { A, Two, Three, Four, Five, Six, Seven, Eight, Nine, Ten, J, Q, K }
public enum Suit { Spades, Hearts, Diamonds, Clubs }
public class Card {
public Card(CardValue value, Suit suit) {
Value = value;
Suit = suit;
}
public CardValue Value { get; private set; }
public Suit Suit { get; private set; }
}
public class Deck : IEnumerable<Card> {
public Deck() {
initialiseDeck();
Shuffle();
}
private Card[] cards = new Card[52];
private void initialiseDeck() {
for (int i = 0; i < 4; ++i) {
for (int j = 0; j < 13; ++j) {
cards[i * 13 + j] = new Card((CardValue)j, (Suit)i);
}
}
}
public void Shuffle() {
Random random = new Random();
for (int i = 0; i < 52; ++i) {
int j = random.Next(51 - i);
// Swap the cards.
Card temp = cards[51 - i];
cards[51 - i] = cards[j];
cards[j] = temp;
}
}
public IEnumerator<Card> GetEnumerator() {
foreach (Card c in cards) yield return c;
}
System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator() {
foreach (Card c in cards) yield return c;
}
}
class Program {
static void Main(string[] args) {
foreach (Card c in new Deck()) {
Console.WriteLine("{0} of {1}", c.Value, c.Suit);
}
Console.ReadKey(true);
}
}
В Haskell:
import Array
problem1 input index = [(left!i) * (right!(i+1)) | i <- index]
where left = scanWith scanl
right = scanWith scanr
scanWith scan = listArray (0, length input) (scan (*) 1 input)
Vaibhav, к сожалению, мы должны принять, что могло быть 0 во входной таблице.
Tnilsson, отличное решение (потому что я сделал это тот же самый путь :P).
Я не вижу никакой другой способ сделать это в линейное время. Кто-либо? Поскольку менеджер по пополнению сказал мне, что это решение не было достаточно эффективным.
Мы пропускаем некоторый супер комплекс, все в одной возвратной линии, решении?
Вторая проблема.
public static void shuffle (int[] array)
{
Random rng = new Random(); // i.e., java.util.Random.
int n = array.length; // The number of items left to shuffle (loop invariant).
while (n > 1)
{
int k = rng.nextInt(n); // 0 <= k < n.
n--; // n is now the last pertinent index;
int temp = array[n]; // swap array[n] with array[k] (does nothing if k == n).
array[n] = array[k];
array[k] = temp;
}
}
Это скопировать/вставить от статьи Википедии о перестановке Фишера-Йетса. O (n) сложность
Tnilsson, я соглашаюсь, что решение YXJuLnphcnQ возможно быстрее, но idee является тем же. Я забыл добавлять, что язык является дополнительным в первой проблеме, а также интервале второе.
Вы правы, который calculationg обнуляет, и интервал продукта, тот же цикл лучше. Возможно, это было вещью.
Tnilsson, у меня есть также uset перестановка Фишера-Йетса :). Я - очень заинтересованное тесто о части тестирования :)
Trilsson сделал отдельную тему о части тестирования вопроса
Как протестировать случайность (рассматриваемый вопрос - Переставляющий)
очень хорошая идея Trilsson:)
YXJuLnphcnQ, это - способ, которым я сделал это также. Это является самым очевидным.
Но факт, что, если Вы пишете алгоритм, который просто переставляет все карты в наборе одно положение направо каждый раз, Вы называете вид (), это прошло бы тест, даже при том, что вывод не случаен.
#include <algorithm>
class Deck {
// each card is 8-bit: 4-bit for suit, 4-bit for value
// suits and values are extracted using bit-magic
char cards[52];
public:
// ...
void shuffle() {
std::random_shuffle(cards, cards + 52);
}
// ...
};
Сложность: Линейный в N. Точно 51 подкачка выполняется. См. http://www.sgi.com/tech/stl/random_shuffle.html
Тестирование:
// ...
int main() {
typedef std::map<std::pair<size_t, Deck::value_type>, size_t> Map;
Map freqs;
Deck d;
const size_t ntests = 100000;
// compute frequencies of events: card at position
for (size_t i = 0; i < ntests; ++i) {
d.shuffle();
size_t pos = 0;
for(Deck::const_iterator j = d.begin(); j != d.end(); ++j, ++pos)
++freqs[std::make_pair(pos, *j)];
}
// if Deck.shuffle() is correct then all frequencies must be similar
for (Map::const_iterator j = freqs.begin(); j != freqs.end(); ++j)
std::cout << "pos=" << j->first.first << " card=" << j->first.second
<< " freq=" << j->second << std::endl;
}
Как обычно, один тест не достаточен.