1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
20 #include "dpitemdata.hxx"
22 #include "document.hxx"
23 #include "dpobject.hxx"
24 #include "formulacell.hxx"
25 #include "globstr.hrc"
26 #include "dptabdat.hxx"
27 #include "rtl/math.hxx"
29 const sal_Int32
ScDPItemData::DateFirst
= -1;
30 const sal_Int32
ScDPItemData::DateLast
= 10000;
32 size_t ScDPItemData::Hash::operator() (const ScDPItemData
& rVal
) const
34 switch (rVal
.GetType())
39 return (size_t)(rVal
.mfValue
);
46 if (rVal
.mbStringInterned
)
47 return reinterpret_cast<size_t>(rVal
.mpString
);
49 OUStringHash aStrHasher
;
50 return aStrHasher(*rVal
.mpString
);
59 sal_Int32
ScDPItemData::Compare(const ScDPItemData
& rA
, const ScDPItemData
& rB
)
61 if (rA
.meType
!= rB
.meType
)
63 // group value, value and string in this order. Ensure that the empty
65 return rA
.meType
< rB
.meType
? -1 : 1;
72 if (rA
.maGroupValue
.mnGroupType
== rB
.maGroupValue
.mnGroupType
)
74 if (rA
.maGroupValue
.mnValue
== rB
.maGroupValue
.mnValue
)
77 return rA
.maGroupValue
.mnValue
< rB
.maGroupValue
.mnValue
? -1 : 1;
80 return rA
.maGroupValue
.mnGroupType
< rB
.maGroupValue
.mnGroupType
? -1 : 1;
85 if (rA
.mfValue
== rB
.mfValue
)
88 return rA
.mfValue
< rB
.mfValue
? -1 : 1;
92 if (rA
.mpString
== rB
.mpString
)
93 // strings may be interned.
96 return ScGlobal::GetCollator()->compareString(rA
.GetString(), rB
.GetString());
103 ScDPItemData::ScDPItemData() :
104 mfValue(0.0), meType(Empty
), mbStringInterned(false) {}
106 ScDPItemData::ScDPItemData(const ScDPItemData
& r
) :
107 meType(r
.meType
), mbStringInterned(r
.mbStringInterned
)
113 mpString
= mbStringInterned
? r
.mpString
: new OUString(*r
.mpString
);
120 maGroupValue
.mnGroupType
= r
.maGroupValue
.mnGroupType
;
121 maGroupValue
.mnValue
= r
.maGroupValue
.mnValue
;
129 void ScDPItemData::DisposeString()
131 if (!mbStringInterned
)
133 if (meType
== String
|| meType
== Error
)
137 mbStringInterned
= false;
140 ScDPItemData::ScDPItemData(const OUString
& rStr
) :
141 mpString(new OUString(rStr
)), meType(String
), mbStringInterned(false) {}
143 ScDPItemData::ScDPItemData(sal_Int32 nGroupType
, sal_Int32 nValue
) :
144 meType(GroupValue
), mbStringInterned(false)
146 maGroupValue
.mnGroupType
= nGroupType
;
147 maGroupValue
.mnValue
= nValue
;
150 ScDPItemData::~ScDPItemData()
155 ScDPItemData::Type
ScDPItemData::GetType() const
157 return static_cast<Type
>(meType
);
160 void ScDPItemData::SetEmpty()
166 void ScDPItemData::SetString(const OUString
& rS
)
169 mpString
= new OUString(rS
);
173 void ScDPItemData::SetString(const OUString
* pS
)
178 mbStringInterned
= true;
181 void ScDPItemData::SetValue(double fVal
)
188 void ScDPItemData::SetRangeStart(double fVal
)
195 void ScDPItemData::SetRangeFirst()
198 rtl::math::setInf(&mfValue
, true);
202 void ScDPItemData::SetRangeLast()
205 rtl::math::setInf(&mfValue
, false);
209 void ScDPItemData::SetErrorString(const OUString
* pS
)
215 bool ScDPItemData::IsCaseInsEqual(const ScDPItemData
& r
) const
217 if (meType
!= r
.meType
)
224 return rtl::math::approxEqual(mfValue
, r
.mfValue
);
226 return maGroupValue
.mnGroupType
== r
.maGroupValue
.mnGroupType
&&
227 maGroupValue
.mnValue
== r
.maGroupValue
.mnValue
;
232 if (mpString
== r
.mpString
)
233 // Fast equality check for interned strings.
236 return ScGlobal::GetpTransliteration()->isEqual(GetString(), r
.GetString());
239 bool ScDPItemData::operator== (const ScDPItemData
& r
) const
241 if (meType
!= r
.meType
)
248 return rtl::math::approxEqual(mfValue
, r
.mfValue
);
250 return maGroupValue
.mnGroupType
== r
.maGroupValue
.mnGroupType
&&
251 maGroupValue
.mnValue
== r
.maGroupValue
.mnValue
;
256 // need exact equality until we have a safe case insensitive string hash
257 return GetString() == r
.GetString();
260 bool ScDPItemData::operator!= (const ScDPItemData
& r
) const
262 return !operator== (r
);
265 bool ScDPItemData::operator< (const ScDPItemData
& r
) const
267 return Compare(*this, r
) == -1;
270 ScDPItemData
& ScDPItemData::operator= (const ScDPItemData
& r
)
274 mbStringInterned
= false;
279 mpString
= r
.mbStringInterned
? r
.mpString
: new OUString(*r
.mpString
);
280 mbStringInterned
= r
.mbStringInterned
;
287 maGroupValue
.mnGroupType
= r
.maGroupValue
.mnGroupType
;
288 maGroupValue
.mnValue
= r
.maGroupValue
.mnValue
;
297 ScDPValue::Type
ScDPItemData::GetCellType() const
302 return ScDPValue::Error
;
304 return ScDPValue::Empty
;
306 return ScDPValue::Value
;
311 return ScDPValue::String
;
314 #if DEBUG_PIVOT_TABLE
316 void ScDPItemData::Dump(const char* msg
) const
318 printf("--- (%s)\n", msg
);
325 printf("error: %s\n",
326 OUStringToOString(*mpString
, RTL_TEXTENCODING_UTF8
).getStr());
329 printf("group value: group type = %d value = %d\n",
330 maGroupValue
.mnGroupType
, maGroupValue
.mnValue
);
333 printf("string: %s\n",
334 OUStringToOString(*mpString
, RTL_TEXTENCODING_UTF8
).getStr());
337 printf("value: %g\n", mfValue
);
340 printf("range start: %g\n", mfValue
);
343 printf("unknown type\n");
349 bool ScDPItemData::IsEmpty() const
351 return meType
== Empty
;
354 bool ScDPItemData::IsValue() const
356 return meType
== Value
;
359 OUString
ScDPItemData::GetString() const
368 return OUString::number(mfValue
);
370 return OUString::number(maGroupValue
.mnValue
);
379 double ScDPItemData::GetValue() const
381 if (meType
== Value
|| meType
== RangeStart
)
387 ScDPItemData::GroupValueAttr
ScDPItemData::GetGroupValue() const
389 if (meType
== GroupValue
)
393 aGV
.mnGroupType
= -1;
398 bool ScDPItemData::HasStringData() const
400 return meType
== String
|| meType
== Error
;
403 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */