Java Source Code: org.json.JSONArray


   1: package org.json;
   2: 
   3: /*
   4: Copyright (c) 2002 JSON.org
   5: 
   6: Permission is hereby granted, free of charge, to any person obtaining a copy
   7: of this software and associated documentation files (the "Software"), to deal
   8: in the Software without restriction, including without limitation the rights
   9: to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  10: copies of the Software, and to permit persons to whom the Software is
  11: furnished to do so, subject to the following conditions:
  12: 
  13: The above copyright notice and this permission notice shall be included in all
  14: copies or substantial portions of the Software.
  15: 
  16: The Software shall be used for Good, not Evil.
  17: 
  18: THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  19: IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  20: FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  21: AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  22: LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  23: OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
  24: SOFTWARE.
  25: */
  26: 
  27: import java.io.IOException;
  28: import java.io.Writer;
  29: import java.util.ArrayList;
  30: import java.util.Collection;
  31: import java.util.Map;
  32: 
  33: /**
  34:  * A JSONArray is an ordered sequence of values. Its external text form is a
  35:  * string wrapped in square brackets with commas separating the values. The
  36:  * internal form is an object having <code>get</code> and <code>opt</code>
  37:  * methods for accessing the values by index, and <code>put</code> methods for
  38:  * adding or replacing values. The values can be any of these types:
  39:  * <code>Boolean</code>, <code>JSONArray</code>, <code>JSONObject</code>,
  40:  * <code>Number</code>, <code>String</code>, or the
  41:  * <code>JSONObject.NULL object</code>.
  42:  * <p>
  43:  * The constructor can convert a JSON text into a Java object. The
  44:  * <code>toString</code> method converts to JSON text.
  45:  * <p>
  46:  * A <code>get</code> method returns a value if one can be found, and throws an
  47:  * exception if one cannot be found. An <code>opt</code> method returns a
  48:  * default value instead of throwing an exception, and so is useful for
  49:  * obtaining optional values.
  50:  * <p>
  51:  * The generic <code>get()</code> and <code>opt()</code> methods return an
  52:  * object which you can cast or query for type. There are also typed
  53:  * <code>get</code> and <code>opt</code> methods that do type checking and type
  54:  * coersion for you.
  55:  * <p>
  56:  * The texts produced by the <code>toString</code> methods strictly conform to
  57:  * JSON syntax rules. The constructors are more forgiving in the texts they will
  58:  * accept:
  59:  * <ul>
  60:  * <li>An extra <code>,</code>&nbsp;<small>(comma)</small> may appear just
  61:  *     before the closing bracket.</li>
  62:  * <li>The <code>null</code> value will be inserted when there
  63:  *     is <code>,</code>&nbsp;<small>(comma)</small> elision.</li>
  64:  * <li>Strings may be quoted with <code>'</code>&nbsp;<small>(single
  65:  *     quote)</small>.</li>
  66:  * <li>Strings do not need to be quoted at all if they do not begin with a quote
  67:  *     or single quote, and if they do not contain leading or trailing spaces,
  68:  *     and if they do not contain any of these characters:
  69:  *     <code>{ } [ ] / \ : , = ; #</code> and if they do not look like numbers
  70:  *     and if they are not the reserved words <code>true</code>,
  71:  *     <code>false</code>, or <code>null</code>.</li>
  72:  * <li>Values can be separated by <code>;</code> <small>(semicolon)</small> as
  73:  *     well as by <code>,</code> <small>(comma)</small>.</li>
  74:  * <li>Numbers may have the <code>0-</code> <small>(octal)</small> or
  75:  *     <code>0x-</code> <small>(hex)</small> prefix.</li>
  76:  * <li>Comments written in the slashshlash, slashstar, and hash conventions
  77:  *     will be ignored.</li>
  78:  * </ul>
  79: 
  80:  * @author JSON.org
  81:  * @version 2
  82:  */
  83:	  public class JSONArray implements JSONString {
  84:
  85:
  86:    /**
  87:     * The arrayList where the JSONArray's properties are kept.
  88:     */
  89:    private ArrayList myArrayList;
  90:
  91:
  92:    /**
  93:     * Construct an empty JSONArray.
  94:     */
  95:	      public JSONArray() {
  96:        this.myArrayList = new ArrayList();
  97:    }
  98:
  99:    /**
 100:     * Construct a JSONArray from a JSONTokener.
 101:     * @param x A JSONTokener
 102:     * @throws JSONException If there is a syntax error.
 103:     */
 104:	      public JSONArray(JSONTokener x) throws JSONException {
 105:        this();
 106:	          if (x.nextClean() != '[') {
 107:            throw x.syntaxError("A JSONArray text must start with '['");
 108:        }
 109:	          if (x.nextClean() == ']') {
 110:            return;
 111:        }
 112:        x.back();
 113:	          for (;;) {
 114:	              if (x.nextClean() == ',') {
 115:                x.back();
 116:                this.myArrayList.add(null);
 117:            } else {
 118:                x.back();
 119:                this.myArrayList.add(x.nextValue());
 120:            }
 121:	              switch (x.nextClean()) {
 122:            case ';':
 123:            case ',':
 124:	                  if (x.nextClean() == ']') {
 125:                    return;
 126:                }
 127:                x.back();
 128:                break;
 129:            case ']':
 130:                return;
 131:            default:
 132:                throw x.syntaxError("Expected a ',' or ']'");
 133:            }
 134:        }
 135:    }
 136:
 137:
 138:    /**
 139:     * Construct a JSONArray from a source sJSON text.
 140:     * @param string     A string that begins with
 141:     * <code>[</code>&nbsp;<small>(left bracket)</small>
 142:     *  and ends with <code>]</code>&nbsp;<small>(right bracket)</small>.
 143:     *  @throws JSONException If there is a syntax error.
 144:     */
 145:	      public JSONArray(String string) throws JSONException {
 146:        this(new JSONTokener(string));
 147:    }
 148:
 149:
 150:    /**
 151:     * Construct a JSONArray from a Collection.
 152:     * @param collection     A Collection.
 153:     */
 154:	      public JSONArray(Collection collection) {
 155:        this.myArrayList = (collection == null) ?
 156:            new ArrayList() :
 157:            new ArrayList(collection);
 158:    }
 159:
 160:
 161:    /**
 162:     * Tests whether or not this array has any elements.
 163:     * @return <code>true</code> if this array is empty; <code>false</code> otherwise
 164:     */
 165:	      public boolean isEmpty() {
 166:        return myArrayList.isEmpty();
 167:    }
 168:
 169:    /**
 170:     * Returns the size of this array.
 171:     * @return the number of elements in this array
 172:     */
 173:	      public int size() {
 174:        return myArrayList.size();
 175:    }
 176:
 177:
 178:    /**
 179:     * Get the object value associated with an index.
 180:     * @param index
 181:     *  The index must be between 0 and length() - 1.
 182:     * @return An object value.
 183:     * @throws JSONException If there is no value for the index.
 184:     */
 185:	      public Object get(int index) throws JSONException {
 186:        Object o = opt(index);
 187:	          if (o == null) {
 188:            throw new JSONException("JSONArray[" + index + "] not found.");
 189:        }
 190:        return o;
 191:    }
 192:
 193:
 194:    /**
 195:     * Get the boolean value associated with an index.
 196:     * The string values "true" and "false" are converted to boolean.
 197:     *
 198:     * @param index The index must be between 0 and length() - 1.
 199:     * @return      The truth.
 200:     * @throws JSONException If there is no value for the index or if the
 201:     *  value is not convertable to boolean.
 202:     */
 203:	      public boolean getBoolean(int index) throws JSONException {
 204:        Object o = get(index);
 205:        if (o.equals(Boolean.FALSE) ||
 206:                (o instanceof String &&
 207:	                  ((String)o).equalsIgnoreCase("false"))) {
 208:            return false;
 209:        } else if (o.equals(Boolean.TRUE) ||
 210:                (o instanceof String &&
 211:	                  ((String)o).equalsIgnoreCase("true"))) {
 212:            return true;
 213:        }
 214:        throw new JSONException("JSONArray[" + index + "] is not a Boolean.");
 215:    }
 216:
 217:
 218:    /**
 219:     * Get the double value associated with an index.
 220:     *
 221:     * @param index The index must be between 0 and length() - 1.
 222:     * @return      The value.
 223:     * @throws   JSONException If the key is not found or if the value cannot
 224:     *  be converted to a number.
 225:     */
 226:	      public double getDouble(int index) throws JSONException {
 227:        Object o = get(index);
 228:	          try {
 229:            return o instanceof Number ?
 230:                ((Number)o).doubleValue() : 
 231:                Double.valueOf((String)o).doubleValue();
 232:        } catch (Exception e) {
 233:            throw new JSONException("JSONArray[" + index +
 234:                "] is not a number.");
 235:        }
 236:    }
 237:
 238:
 239:    /**
 240:     * Get the int value associated with an index.
 241:     *
 242:     * @param index The index must be between 0 and length() - 1.
 243:     * @return      The value.
 244:     * @throws   JSONException If the key is not found or if the value cannot
 245:     *  be converted to a number.
 246:     *  if the value cannot be converted to a number.
 247:     */
 248:	      public int getInt(int index) throws JSONException {
 249:        Object o = get(index);
 250:        return o instanceof Number ?
 251:                ((Number)o).intValue() : (int)getDouble(index);
 252:    }
 253:
 254:
 255:    /**
 256:     * Get the JSONArray associated with an index.
 257:     * @param index The index must be between 0 and length() - 1.
 258:     * @return      A JSONArray value.
 259:     * @throws JSONException If there is no value for the index. or if the
 260:     * value is not a JSONArray
 261:     */
 262:	      public JSONArray getJSONArray(int index) throws JSONException {
 263:        Object o = get(index);
 264:	          if (o instanceof JSONArray) {
 265:            return (JSONArray)o;
 266:        }
 267:        throw new JSONException("JSONArray[" + index +
 268:                "] is not a JSONArray.");
 269:    }
 270:
 271:
 272:    /**
 273:     * Get the JSONObject associated with an index.
 274:     * @param index subscript
 275:     * @return      A JSONObject value.
 276:     * @throws JSONException If there is no value for the index or if the
 277:     * value is not a JSONObject
 278:     */
 279:	      public JSONObject getJSONObject(int index) throws JSONException {
 280:        Object o = get(index);
 281:	          if (o instanceof JSONObject) {
 282:            return (JSONObject)o;
 283:        }
 284:        throw new JSONException("JSONArray[" + index +
 285:            "] is not a JSONObject.");
 286:    }
 287:
 288:
 289:    /**
 290:     * Get the long value associated with an index.
 291:     *
 292:     * @param index The index must be between 0 and length() - 1.
 293:     * @return      The value.
 294:     * @throws   JSONException If the key is not found or if the value cannot
 295:     *  be converted to a number.
 296:     */
 297:	      public long getLong(int index) throws JSONException {
 298:        Object o = get(index);
 299:        return o instanceof Number ?
 300:                ((Number)o).longValue() : (long)getDouble(index);
 301:    }
 302:
 303:
 304:    /**
 305:     * Get the string associated with an index.
 306:     * @param index The index must be between 0 and length() - 1.
 307:     * @return      A string value.
 308:     * @throws JSONException If there is no value for the index.
 309:     */
 310:	      public String getString(int index) throws JSONException {
 311:        return get(index).toString();
 312:    }
 313:
 314:
 315:    /**
 316:     * Determine if the value is null.
 317:     * @param index The index must be between 0 and length() - 1.
 318:     * @return true if the value at the index is null, or if there is no value.
 319:     */
 320:	      public boolean isNull(int index) {
 321:        return JSONObject.NULL.equals(opt(index));
 322:    }
 323:
 324:
 325:    /**
 326:     * Make a string from the contents of this JSONArray. The
 327:     * <code>separator</code> string is inserted between each element.
 328:     * Warning: This method assumes that the data structure is acyclical.
 329:     * @param separator A string that will be inserted between the elements.
 330:     * @return a string.
 331:     * @throws JSONException If the array contains an invalid number.
 332:     */
 333:	      public String join(String separator) throws JSONException {
 334:        int len = length();
 335:        StringBuffer sb = new StringBuffer();
 336:
 337:	          for (int i = 0; i < len; i += 1) {
 338:	              if (i > 0) {
 339:                sb.append(separator);
 340:            }
 341:            sb.append(JSONObject.valueToString(this.myArrayList.get(i)));
 342:        }
 343:        return sb.toString();
 344:    }
 345:
 346:
 347:    /**
 348:     * Get the number of elements in the JSONArray, included nulls.
 349:     *
 350:     * @return The length (or size).
 351:     */
 352:	      public int length() {
 353:        return this.myArrayList.size();
 354:    }
 355:
 356:
 357:    /**
 358:     * Get the optional object value associated with an index.
 359:     * @param index The index must be between 0 and length() - 1.
 360:     * @return      An object value, or null if there is no
 361:     *              object at that index.
 362:     */
 363:	      public Object opt(int index) {
 364:        return (index < 0 || index >= length()) ?
 365:            null : this.myArrayList.get(index);
 366:    }
 367:
 368:
 369:    /**
 370:     * Get the optional boolean value associated with an index.
 371:     * It returns false if there is no value at that index,
 372:     * or if the value is not Boolean.TRUE or the String "true".
 373:     *
 374:     * @param index The index must be between 0 and length() - 1.
 375:     * @return      The truth.
 376:     */
 377:	      public boolean optBoolean(int index)  {
 378:        return optBoolean(index, false);
 379:    }
 380:
 381:
 382:    /**
 383:     * Get the optional boolean value associated with an index.
 384:     * It returns the defaultValue if there is no value at that index or if
 385:     * it is not a Boolean or the String "true" or "false" (case insensitive).
 386:     *
 387:     * @param index The index must be between 0 and length() - 1.
 388:     * @param defaultValue     A boolean default.
 389:     * @return      The truth.
 390:     */
 391:	      public boolean optBoolean(int index, boolean defaultValue)  {
 392:	          try {
 393:            return getBoolean(index);
 394:        } catch (Exception e) {
 395:            return defaultValue;
 396:        }
 397:    }
 398:
 399:
 400:    /**
 401:     * Get the optional double value associated with an index.
 402:     * NaN is returned if there is no value for the index,
 403:     * or if the value is not a number and cannot be converted to a number.
 404:     *
 405:     * @param index The index must be between 0 and length() - 1.
 406:     * @return      The value.
 407:     */
 408:	      public double optDouble(int index) {
 409:        return optDouble(index, Double.NaN);
 410:    }
 411:
 412:
 413:    /**
 414:     * Get the optional double value associated with an index.
 415:     * The defaultValue is returned if there is no value for the index,
 416:     * or if the value is not a number and cannot be converted to a number.
 417:     *
 418:     * @param index subscript
 419:     * @param defaultValue     The default value.
 420:     * @return      The value.
 421:     */
 422:	      public double optDouble(int index, double defaultValue) {
 423:	          try {
 424:            return getDouble(index);
 425:        } catch (Exception e) {
 426:            return defaultValue;
 427:        }
 428:    }
 429:
 430:
 431:    /**
 432:     * Get the optional int value associated with an index.
 433:     * Zero is returned if there is no value for the index,
 434:     * or if the value is not a number and cannot be converted to a number.
 435:     *
 436:     * @param index The index must be between 0 and length() - 1.
 437:     * @return      The value.
 438:     */
 439:	      public int optInt(int index) {
 440:        return optInt(index, 0);
 441:    }
 442:
 443:
 444:    /**
 445:     * Get the optional int value associated with an index.
 446:     * The defaultValue is returned if there is no value for the index,
 447:     * or if the value is not a number and cannot be converted to a number.
 448:     * @param index The index must be between 0 and length() - 1.
 449:     * @param defaultValue     The default value.
 450:     * @return      The value.
 451:     */
 452:	      public int optInt(int index, int defaultValue) {
 453:	          try {
 454:            return getInt(index);
 455:        } catch (Exception e) {
 456:            return defaultValue;
 457:        }
 458:    }
 459:
 460:
 461:    /**
 462:     * Get the optional JSONArray associated with an index.
 463:     * @param index subscript
 464:     * @return      A JSONArray value, or null if the index has no value,
 465:     * or if the value is not a JSONArray.
 466:     */
 467:	      public JSONArray optJSONArray(int index) {
 468:        Object o = opt(index);
 469:        return o instanceof JSONArray ? (JSONArray)o : null;
 470:    }
 471:
 472:
 473:    /**
 474:     * Get the optional JSONObject associated with an index.
 475:     * Null is returned if the key is not found, or null if the index has
 476:     * no value, or if the value is not a JSONObject.
 477:     *
 478:     * @param index The index must be between 0 and length() - 1.
 479:     * @return      A JSONObject value.
 480:     */
 481:	      public JSONObject optJSONObject(int index) {
 482:        Object o = opt(index);
 483:        return o instanceof JSONObject ? (JSONObject)o : null;
 484:    }
 485:
 486:
 487:    /**
 488:     * Get the optional long value associated with an index.
 489:     * Zero is returned if there is no value for the index,
 490:     * or if the value is not a number and cannot be converted to a number.
 491:     *
 492:     * @param index The index must be between 0 and length() - 1.
 493:     * @return      The value.
 494:     */
 495:	      public long optLong(int index) {
 496:        return optLong(index, 0);
 497:    }
 498:
 499:
 500:    /**
 501:     * Get the optional long value associated with an index.
 502:     * The defaultValue is returned if there is no value for the index,
 503:     * or if the value is not a number and cannot be converted to a number.
 504:     * @param index The index must be between 0 and length() - 1.
 505:     * @param defaultValue     The default value.
 506:     * @return      The value.
 507:     */
 508:	      public long optLong(int index, long defaultValue) {
 509:	          try {
 510:            return getLong(index);
 511:        } catch (Exception e) {
 512:            return defaultValue;
 513:        }
 514:    }
 515:
 516:
 517:    /**
 518:     * Get the optional string value associated with an index. It returns an
 519:     * empty string if there is no value at that index. If the value
 520:     * is not a string and is not null, then it is coverted to a string.
 521:     *
 522:     * @param index The index must be between 0 and length() - 1.
 523:     * @return      A String value.
 524:     */
 525:	      public String optString(int index) {
 526:        return optString(index, "");
 527:    }
 528:
 529:
 530:    /**
 531:     * Get the optional string associated with an index.
 532:     * The defaultValue is returned if the key is not found.
 533:     *
 534:     * @param index The index must be between 0 and length() - 1.
 535:     * @param defaultValue     The default value.
 536:     * @return      A String value.
 537:     */
 538:	      public String optString(int index, String defaultValue) {
 539:        Object o = opt(index);
 540:        return o != null ? o.toString() : defaultValue;
 541:    }
 542:
 543:
 544:    /**
 545:     * Append a boolean value. This increases the array's length by one.
 546:     *
 547:     * @param value A boolean value.
 548:     * @return this.
 549:     */
 550:	      public JSONArray put(boolean value) {
 551:        put(value ? Boolean.TRUE : Boolean.FALSE);
 552:        return this;
 553:    }
 554:
 555:
 556:    /**
 557:     * Put a value in the JSONArray, where the value will be a
 558:     * JSONArray which is produced from a Collection.
 559:     * @param value    A Collection value.
 560:     * @return        this.
 561:     */
 562:	      public JSONArray put(Collection value) {
 563:        put(new JSONArray(value));
 564:        return this;
 565:    }
 566:    
 567:
 568:    /**
 569:     * Append a double value. This increases the array's length by one.
 570:     *
 571:     * @param value A double value.
 572:     * @throws JSONException if the value is not finite.
 573:     * @return this.
 574:     */
 575:	      public JSONArray put(double value) throws JSONException {
 576:        Double d = new Double(value);
 577:        JSONObject.testValidity(d);
 578:        put(d);
 579:        return this;
 580:    }
 581:
 582:
 583:    /**
 584:     * Append an int value. This increases the array's length by one.
 585:     *
 586:     * @param value An int value.
 587:     * @return this.
 588:     */
 589:	      public JSONArray put(int value) {
 590:        put(new Integer(value));
 591:        return this;
 592:    }
 593:
 594:
 595:    /**
 596:     * Append an long value. This increases the array's length by one.
 597:     *
 598:     * @param value A long value.
 599:     * @return this.
 600:     */
 601:	      public JSONArray put(long value) {
 602:        put(new Long(value));
 603:        return this;
 604:    }
 605:
 606:
 607:    /**
 608:     * Put a value in the JSONArray, where the value will be a
 609:     * JSONObject which is produced from a Map.
 610:     * @param value    A Map value.
 611:     * @return        this.
 612:     */
 613:	      public JSONArray put(Map value) {
 614:        put(new JSONObject(value));
 615:        return this;
 616:    }
 617:    
 618:    
 619:    /**
 620:     * Append an object value. This increases the array's length by one.
 621:     * @param value An object value.  The value should be a
 622:     *  Boolean, Double, Integer, JSONArray, JSONObject, Long, or String, or the
 623:     *  JSONObject.NULL object.
 624:     * @return this.
 625:     */
 626:	      public JSONArray put(Object value) {
 627:        this.myArrayList.add(value);
 628:        return this;
 629:    }
 630:
 631:
 632:    /**
 633:     * Put or replace a boolean value in the JSONArray. If the index is greater
 634:     * than the length of the JSONArray, then null elements will be added as
 635:     * necessary to pad it out.
 636:     * @param index The subscript.
 637:     * @param value A boolean value.
 638:     * @return this.
 639:     * @throws JSONException If the index is negative.
 640:     */
 641:	      public JSONArray put(int index, boolean value) throws JSONException {
 642:        put(index, value ? Boolean.TRUE : Boolean.FALSE);
 643:        return this;
 644:    }
 645:
 646:    
 647:    /**
 648:     * Put a value in the JSONArray, where the value will be a
 649:     * JSONArray which is produced from a Collection.
 650:     * @param index The subscript.
 651:     * @param value    A Collection value.
 652:     * @return        this.
 653:     * @throws JSONException If the index is negative or if the value is
 654:     * not finite.
 655:     */
 656:	      public JSONArray put(int index, Collection value) throws JSONException {
 657:        put(index, new JSONArray(value));
 658:        return this;
 659:    }
 660:
 661:    
 662:    /**
 663:     * Put or replace a double value. If the index is greater than the length of
 664:     *  the JSONArray, then null elements will be added as necessary to pad
 665:     *  it out.
 666:     * @param index The subscript.
 667:     * @param value A double value.
 668:     * @return this.
 669:     * @throws JSONException If the index is negative or if the value is
 670:     * not finite.
 671:     */
 672:	      public JSONArray put(int index, double value) throws JSONException {
 673:        put(index, new Double(value));
 674:        return this;
 675:    }
 676:
 677:
 678:    /**
 679:     * Put or replace an int value. If the index is greater than the length of
 680:     *  the JSONArray, then null elements will be added as necessary to pad
 681:     *  it out.
 682:     * @param index The subscript.
 683:     * @param value An int value.
 684:     * @return this.
 685:     * @throws JSONException If the index is negative.
 686:     */
 687:	      public JSONArray put(int index, int value) throws JSONException {
 688:        put(index, new Integer(value));
 689:        return this;
 690:    }
 691:
 692:
 693:    /**
 694:     * Put or replace a long value. If the index is greater than the length of
 695:     *  the JSONArray, then null elements will be added as necessary to pad
 696:     *  it out.
 697:     * @param index The subscript.
 698:     * @param value A long value.
 699:     * @return this.
 700:     * @throws JSONException If the index is negative.
 701:     */
 702:	      public JSONArray put(int index, long value) throws JSONException {
 703:        put(index, new Long(value));
 704:        return this;
 705:    }
 706:
 707:
 708:    /**
 709:     * Put a value in the JSONArray, where the value will be a
 710:     * JSONObject which is produced from a Map.
 711:     * @param index The subscript.
 712:     * @param value    The Map value.
 713:     * @return        this.
 714:     * @throws JSONException If the index is negative or if the the value is
 715:     *  an invalid number.
 716:     */
 717:	      public JSONArray put(int index, Map value) throws JSONException {
 718:        put(index, new JSONObject(value));
 719:        return this;
 720:    }
 721:    
 722:    
 723:    /**
 724:     * Put or replace an object value in the JSONArray. If the index is greater
 725:     *  than the length of the JSONArray, then null elements will be added as
 726:     *  necessary to pad it out.
 727:     * @param index The subscript.
 728:     * @param value The value to put into the array. The value should be a
 729:     *  Boolean, Double, Integer, JSONArray, JSONObject, Long, or String, or the
 730:     *  JSONObject.NULL object.
 731:     * @return this.
 732:     * @throws JSONException If the index is negative or if the the value is
 733:     *  an invalid number.
 734:     */
 735:	      public JSONArray put(int index, Object value) throws JSONException {
 736:        JSONObject.testValidity(value);
 737:	          if (index < 0) {
 738:            throw new JSONException("JSONArray[" + index + "] not found.");
 739:        }
 740:	          if (index < length()) {
 741:            this.myArrayList.set(index, value);
 742:        } else {
 743:	              while (index != length()) {
 744:                put(JSONObject.NULL);
 745:            }
 746:            put(value);
 747:        }
 748:        return this;
 749:    }
 750:
 751:
 752:    /**
 753:     * Produce a JSONObject by combining a JSONArray of names with the values
 754:     * of this JSONArray.
 755:     * @param names A JSONArray containing a list of key strings. These will be
 756:     * paired with the values.
 757:     * @return A JSONObject, or null if there are no names or if this JSONArray
 758:     * has no values.
 759:     * @throws JSONException If any of the names are null.
 760:     */
 761:	      public JSONObject toJSONObject(JSONArray names) throws JSONException {
 762:	          if (names == null || names.length() == 0 || length() == 0) {
 763:            return null;
 764:        }
 765:        JSONObject jo = new JSONObject();
 766:	          for (int i = 0; i < names.length(); i += 1) {
 767:            jo.put(names.getString(i), this.opt(i));
 768:        }
 769:        return jo;
 770:    }
 771:
 772:    
 773:    /**
 774:     * Returns this object in JSON form by calling toString().
 775:     * 
 776:     * @return this object in JSON form
 777:     */
 778:	      public String toJSONString() {
 779:        return toString();
 780:    }
 781:
 782:    /**
 783:     * Make a JSON text of this JSONArray. For compactness, no
 784:     * unnecessary whitespace is added. If it is not possible to produce a
 785:     * syntactically correct JSON text then null will be returned instead. This
 786:     * could occur if the array contains an invalid number.
 787:     * <p>
 788:     * Warning: This method assumes that the data structure is acyclical.
 789:     *
 790:     * @return a printable, displayable, transmittable
 791:     *  representation of the array.
 792:     */
 793:	      public String toString() {
 794:	          try {
 795:            return '[' + join(",") + ']';
 796:        } catch (Exception e) {
 797:            return null;
 798:        }
 799:    }
 800:
 801:
 802:    /**
 803:     * Make a prettyprinted JSON text of this JSONArray.
 804:     * Warning: This method assumes that the data structure is acyclical.
 805:     * @param indentFactor The number of spaces to add to each level of
 806:     *  indentation.
 807:     * @return a printable, displayable, transmittable
 808:     *  representation of the object, beginning
 809:     *  with <code>[</code>&nbsp;<small>(left bracket)</small> and ending
 810:     *  with <code>]</code>&nbsp;<small>(right bracket)</small>.
 811:     * @throws JSONException
 812:     */
 813:	      public String toString(int indentFactor) throws JSONException {
 814:        return toString(indentFactor, 0);
 815:    }
 816:
 817:
 818:    /**
 819:     * Make a prettyprinted JSON text of this JSONArray.
 820:     * Warning: This method assumes that the data structure is acyclical.
 821:     * @param indentFactor The number of spaces to add to each level of
 822:     *  indentation.
 823:     * @param indent The indention of the top level.
 824:     * @return a printable, displayable, transmittable
 825:     *  representation of the array.
 826:     * @throws JSONException
 827:     */
 828:	      String toString(int indentFactor, int indent) throws JSONException {
 829:        int len = length();
 830:	          if (len == 0) {
 831:            return "[]";
 832:        }
 833:        int i;
 834:        StringBuffer sb = new StringBuffer("[");
 835:	          if (len == 1) {
 836:            sb.append(JSONObject.valueToString(this.myArrayList.get(0),
 837:                    indentFactor, indent));
 838:        } else {
 839:            int newindent = indent + indentFactor;
 840:            sb.append('\n');
 841:	              for (i = 0; i < len; i += 1) {
 842:	                  if (i > 0) {
 843:                    sb.append(",\n");
 844:                }
 845:	                  for (int j = 0; j < newindent; j += 1) {
 846:                    sb.append(' ');
 847:                }
 848:                sb.append(JSONObject.valueToString(this.myArrayList.get(i),
 849:                        indentFactor, newindent));
 850:            }
 851:            sb.append('\n');
 852:	              for (i = 0; i < indent; i += 1) {
 853:                sb.append(' ');
 854:            }
 855:        }
 856:        sb.append(']');
 857:        return sb.toString();
 858:    }
 859:
 860:
 861:    /**
 862:     * Write the contents of the JSONArray as JSON text to a writer.
 863:     * For compactness, no whitespace is added.
 864:     * <p>
 865:     * Warning: This method assumes that the data structure is acyclical.
 866:     *
 867:     * @return The writer.
 868:     * @throws JSONException
 869:     */
 870:	      public Writer write(Writer writer) throws JSONException {
 871:	          try {
 872:            boolean b = false;
 873:            int     len = length();
 874:
 875:            writer.write('[');
 876:
 877:	              for (int i = 0; i < len; i += 1) {
 878:	                  if (b) {
 879:                    writer.write(',');
 880:                }
 881:                Object v = this.myArrayList.get(i);
 882:	                  if (v instanceof JSONObject) {
 883:                    ((JSONObject)v).write(writer);
 884:                } else if (v instanceof JSONArray) {
 885:                    ((JSONArray)v).write(writer);
 886:                } else {
 887:                    writer.write(JSONObject.valueToString(v));
 888:                }
 889:                b = true;
 890:            }
 891:            writer.write(']');
 892:            return writer;
 893:        } catch (IOException e) {
 894:           throw new JSONException(e);
 895:        }
 896:    }
 897:}