예제 #1
0
void iterateArray(Value::ConstValueIterator& itr,
		Value::ConstValueIterator& itrEnd, StringBuffer *buffer,
		Writer<StringBuffer> *writer, stringstream& ss) {
	for (; itr != itrEnd; itr++) {
		if (itr->IsObject()) {
			Value::ConstMemberIterator itr_ = itr->MemberBegin();
			Value::ConstMemberIterator itrEnd_ = itr->MemberEnd();
			iterateObject(itr_, itrEnd_, buffer, writer, ss);
		} else if (itr->IsArray()) {
			Value::ConstValueIterator itr_ = itr->Begin();
			Value::ConstValueIterator itrEnd_ = itr->End();
			iterateArray(itr_, itrEnd_, buffer, writer, ss);
		} else if (itr->IsBool()) {
			ss << DELIM << itr->GetBool();
		} else if (itr->IsInt()) {
			ss << DELIM << itr->GetInt();
		} else if (itr->IsInt64()) {
			ss << DELIM << itr->GetInt64();
		} else if (itr->IsDouble()) {
			ss << DELIM << itr->GetDouble();
		} else if (itr->IsString()) {
			ss << DELIM << "\"" << itr->GetString() << "\"";
		} else {
			throw runtime_error(string("Case missing from tokenizer"));
		}
	}
}
예제 #2
0
TEST(Value, Array) {
    Value x(kArrayType);
    const Value& y = x;
    Value::AllocatorType allocator;

    EXPECT_EQ(kArrayType, x.GetType());
    EXPECT_TRUE(x.IsArray());
    EXPECT_TRUE(x.Empty());
    EXPECT_EQ(0u, x.Size());
    EXPECT_TRUE(y.IsArray());
    EXPECT_TRUE(y.Empty());
    EXPECT_EQ(0u, y.Size());

    EXPECT_FALSE(x.IsNull());
    EXPECT_FALSE(x.IsBool());
    EXPECT_FALSE(x.IsFalse());
    EXPECT_FALSE(x.IsTrue());
    EXPECT_FALSE(x.IsString());
    EXPECT_FALSE(x.IsObject());

    // PushBack()
    Value v;
    x.PushBack(v, allocator);
    v.SetBool(true);
    x.PushBack(v, allocator);
    v.SetBool(false);
    x.PushBack(v, allocator);
    v.SetInt(123);
    x.PushBack(v, allocator);
    //x.PushBack((const char*)"foo", allocator); // should not compile
    x.PushBack("foo", allocator);

    EXPECT_FALSE(x.Empty());
    EXPECT_EQ(5u, x.Size());
    EXPECT_FALSE(y.Empty());
    EXPECT_EQ(5u, y.Size());
    EXPECT_TRUE(x[SizeType(0)].IsNull());
    EXPECT_TRUE(x[1].IsTrue());
    EXPECT_TRUE(x[2].IsFalse());
    EXPECT_TRUE(x[3].IsInt());
    EXPECT_EQ(123, x[3].GetInt());
    EXPECT_TRUE(y[SizeType(0)].IsNull());
    EXPECT_TRUE(y[1].IsTrue());
    EXPECT_TRUE(y[2].IsFalse());
    EXPECT_TRUE(y[3].IsInt());
    EXPECT_EQ(123, y[3].GetInt());
    EXPECT_TRUE(y[4].IsString());
    EXPECT_STREQ("foo", y[4].GetString());

#if RAPIDJSON_HAS_CXX11_RVALUE_REFS
    // PushBack(GenericValue&&, Allocator&);
    {
        Value y(kArrayType);
        y.PushBack(Value(true), allocator);
        y.PushBack(std::move(Value(kArrayType).PushBack(Value(1), allocator).PushBack("foo", allocator)), allocator);
        EXPECT_EQ(2u, y.Size());
        EXPECT_TRUE(y[0].IsTrue());
        EXPECT_TRUE(y[1].IsArray());
        EXPECT_EQ(2u, y[1].Size());
        EXPECT_TRUE(y[1][0].IsInt());
        EXPECT_TRUE(y[1][1].IsString());
    }
#endif

    // iterator
    Value::ValueIterator itr = x.Begin();
    EXPECT_TRUE(itr != x.End());
    EXPECT_TRUE(itr->IsNull());
    ++itr;
    EXPECT_TRUE(itr != x.End());
    EXPECT_TRUE(itr->IsTrue());
    ++itr;
    EXPECT_TRUE(itr != x.End());
    EXPECT_TRUE(itr->IsFalse());
    ++itr;
    EXPECT_TRUE(itr != x.End());
    EXPECT_TRUE(itr->IsInt());
    EXPECT_EQ(123, itr->GetInt());
    ++itr;
    EXPECT_TRUE(itr != x.End());
    EXPECT_TRUE(itr->IsString());
    EXPECT_STREQ("foo", itr->GetString());

    // const iterator
    Value::ConstValueIterator citr = y.Begin();
    EXPECT_TRUE(citr != y.End());
    EXPECT_TRUE(citr->IsNull());
    ++citr;
    EXPECT_TRUE(citr != y.End());
    EXPECT_TRUE(citr->IsTrue());
    ++citr;
    EXPECT_TRUE(citr != y.End());
    EXPECT_TRUE(citr->IsFalse());
    ++citr;
    EXPECT_TRUE(citr != y.End());
    EXPECT_TRUE(citr->IsInt());
    EXPECT_EQ(123, citr->GetInt());
    ++citr;
    EXPECT_TRUE(citr != y.End());
    EXPECT_TRUE(citr->IsString());
    EXPECT_STREQ("foo", citr->GetString());

    // PopBack()
    x.PopBack();
    EXPECT_EQ(4u, x.Size());
    EXPECT_TRUE(y[SizeType(0)].IsNull());
    EXPECT_TRUE(y[1].IsTrue());
    EXPECT_TRUE(y[2].IsFalse());
    EXPECT_TRUE(y[3].IsInt());

    // Clear()
    x.Clear();
    EXPECT_TRUE(x.Empty());
    EXPECT_EQ(0u, x.Size());
    EXPECT_TRUE(y.Empty());
    EXPECT_EQ(0u, y.Size());

    // Erase(ValueIterator)

    // Use array of array to ensure removed elements' destructor is called.
    // [[0],[1],[2],...]
    for (int i = 0; i < 10; i++)
        x.PushBack(Value(kArrayType).PushBack(i, allocator).Move(), allocator);

    // Erase the first
    itr = x.Erase(x.Begin());
    EXPECT_EQ(x.Begin(), itr);
    EXPECT_EQ(9u, x.Size());
    for (int i = 0; i < 9; i++)
        EXPECT_EQ(i + 1, x[static_cast<SizeType>(i)][0].GetInt());

    // Ease the last
    itr = x.Erase(x.End() - 1);
    EXPECT_EQ(x.End(), itr);
    EXPECT_EQ(8u, x.Size());
    for (int i = 0; i < 8; i++)
        EXPECT_EQ(i + 1, x[static_cast<SizeType>(i)][0].GetInt());

    // Erase the middle
    itr = x.Erase(x.Begin() + 4);
    EXPECT_EQ(x.Begin() + 4, itr);
    EXPECT_EQ(7u, x.Size());
    for (int i = 0; i < 4; i++)
        EXPECT_EQ(i + 1, x[static_cast<SizeType>(i)][0].GetInt());
    for (int i = 4; i < 7; i++)
        EXPECT_EQ(i + 2, x[static_cast<SizeType>(i)][0].GetInt());

    // Erase(ValueIterator, ValueIterator)
    // Exhaustive test with all 0 <= first < n, first <= last <= n cases
    const unsigned n = 10;
    for (unsigned first = 0; first < n; first++) {
        for (unsigned last = first; last <= n; last++) {
            x.Clear();
            for (unsigned i = 0; i < n; i++)
                x.PushBack(Value(kArrayType).PushBack(i, allocator).Move(), allocator);
            
            itr = x.Erase(x.Begin() + first, x.Begin() + last);
            if (last == n)
                EXPECT_EQ(x.End(), itr);
            else
                EXPECT_EQ(x.Begin() + first, itr);

            size_t removeCount = last - first;
            EXPECT_EQ(n - removeCount, x.Size());
            for (unsigned i = 0; i < first; i++)
                EXPECT_EQ(i, x[i][0].GetUint());
            for (unsigned i = first; i < n - removeCount; i++)
                EXPECT_EQ(i + removeCount, x[static_cast<SizeType>(i)][0].GetUint());
        }
    }

    // Working in gcc without C++11, but VS2013 cannot compile. To be diagnosed.
    // http://en.wikipedia.org/wiki/Erase-remove_idiom
    x.Clear();
    for (int i = 0; i < 10; i++)
        if (i % 2 == 0)
            x.PushBack(i, allocator);
        else
            x.PushBack(Value(kNullType).Move(), allocator);

    const Value null(kNullType);
    x.Erase(std::remove(x.Begin(), x.End(), null), x.End());
    EXPECT_EQ(5u, x.Size());
    for (int i = 0; i < 5; i++)
        EXPECT_EQ(i * 2, x[static_cast<SizeType>(i)]);

    // SetArray()
    Value z;
    z.SetArray();
    EXPECT_TRUE(z.IsArray());
    EXPECT_TRUE(z.Empty());
}
예제 #3
0
std::vector<SlotType>
MtgJsonAllSetsData::getBoosterSlots( const std::string& code ) const
{
    std::vector<SlotType> boosterSlots;

    if( mBoosterSetCodes.count(code) == 0 )
    {
        mLogger->warn( "No booster member in set {}, returning empty booster slots", code );
        return boosterSlots;
    }

    // In parse() this was vetted to be safe and yield an Array-type value.
    const Value& boosterValue = mDoc[code]["booster"];

    mLogger->debug( "{:-^40}", "assembling booster slots" );
    for( Value::ConstValueIterator iter = boosterValue.Begin(); iter != boosterValue.End(); ++iter )
    {
        if( iter->IsArray() )
        {
            // create a set of any strings in the array
            std::set<std::string> slotArraySet;
            for( unsigned i = 0; i < iter->Size(); ++i )
            {
                const Value& val = (*iter)[i];
                if( val.IsString() )
                {
                    slotArraySet.insert( val.GetString() );
                    mLogger->debug( "booster slot array[{}]: {}", i, val.GetString() );
                }
                else
                {
                    mLogger->warn( "Non-string in booster slot array, ignoring!" );
                }
            }
            const std::set<std::string> rareMythicRareSlot { "rare", "mythic rare" };
            if( slotArraySet == rareMythicRareSlot )
                boosterSlots.push_back( SLOT_RARE_OR_MYTHIC_RARE );
            else
                mLogger->warn( "Unrecognized booster slot array, ignoring!" );
        }
        else if( iter->IsString() )
        {
            std::string slotStr( iter->GetString() );
            mLogger->debug( "booster slot string: {}", slotStr );
            if( slotStr == "common" )
                boosterSlots.push_back( SLOT_COMMON );
            else if( slotStr == "uncommon" )
                boosterSlots.push_back( SLOT_UNCOMMON );
            else if( slotStr == "rare" )
                boosterSlots.push_back( SLOT_RARE );
            else if( slotStr == "timeshifted purple" )
                boosterSlots.push_back( SLOT_TIMESHIFTED_PURPLE );
            else if( slotStr == "land" )      { /* do nothing */ }
            else if( slotStr == "marketing" ) { /* do nothing */ }
            else
                mLogger->warn( "Unrecognized booster slot type {}, ignoring!", slotStr );
        }
        else
        {
            mLogger->warn( "Non-string booster slot type, ignoring!" );
        }
    }
    return boosterSlots;
}