You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@pig.apache.org by da...@apache.org on 2014/02/03 20:56:03 UTC
svn commit: r1564034 - in /pig/trunk: CHANGES.txt
contrib/piggybank/java/src/main/java/org/apache/pig/piggybank/evaluation/string/Stuff.java
contrib/piggybank/java/src/test/java/org/apache/pig/piggybank/test/evaluation/string/TestStuff.java
Author: daijy
Date: Mon Feb 3 19:56:03 2014
New Revision: 1564034
URL: http://svn.apache.org/r1564034
Log:
PIG-3238: Pig current releases lack a UDF Stuff(). This UDF deletes a specified length of characters and inserts another set of characters at a specified starting point
Added:
pig/trunk/contrib/piggybank/java/src/main/java/org/apache/pig/piggybank/evaluation/string/Stuff.java
pig/trunk/contrib/piggybank/java/src/test/java/org/apache/pig/piggybank/test/evaluation/string/TestStuff.java
Modified:
pig/trunk/CHANGES.txt
Modified: pig/trunk/CHANGES.txt
URL: http://svn.apache.org/viewvc/pig/trunk/CHANGES.txt?rev=1564034&r1=1564033&r2=1564034&view=diff
==============================================================================
--- pig/trunk/CHANGES.txt (original)
+++ pig/trunk/CHANGES.txt Mon Feb 3 19:56:03 2014
@@ -30,6 +30,9 @@ PIG-2207: Support custom counters for ag
IMPROVEMENTS
+PIG-3238: Pig current releases lack a UDF Stuff(). This UDF deletes a specified length of characters
+ and inserts another set of characters at a specified starting point (nezihyigitbasi via daijy)
+
PIG-3299: Provide support for LazyOutputFormat to avoid creating empty files (lbendig via daijy)
PIG-3642: Direct HDFS access for small jobs (fetch) (lbendig via cheolsoo)
Added: pig/trunk/contrib/piggybank/java/src/main/java/org/apache/pig/piggybank/evaluation/string/Stuff.java
URL: http://svn.apache.org/viewvc/pig/trunk/contrib/piggybank/java/src/main/java/org/apache/pig/piggybank/evaluation/string/Stuff.java?rev=1564034&view=auto
==============================================================================
--- pig/trunk/contrib/piggybank/java/src/main/java/org/apache/pig/piggybank/evaluation/string/Stuff.java (added)
+++ pig/trunk/contrib/piggybank/java/src/main/java/org/apache/pig/piggybank/evaluation/string/Stuff.java Mon Feb 3 19:56:03 2014
@@ -0,0 +1,117 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.pig.piggybank.evaluation.string;
+
+import java.io.IOException;
+
+import org.apache.pig.EvalFunc;
+import org.apache.pig.PigWarning;
+import org.apache.pig.data.DataType;
+import org.apache.pig.data.Tuple;
+import org.apache.pig.impl.logicalLayer.schema.Schema;
+
+/**
+ * Given a string, this UDF replaces a substring given its starting index and
+ * length with the given replacement string. If the the last argument is null, the specified
+ * part of the string gets deleted.
+ *
+ * B = FOREACH A GENERATE Stuff($0, 10, 4, 'Pie')
+ * If $0 is "Chocolate Cake" then the UDF will return "Chocolate Pie"
+ *
+ **/
+
+public class Stuff extends EvalFunc<String> {
+
+ public String exec(Tuple input) throws IOException {
+ int inputSize = input.size();
+
+ if (input == null || inputSize == 0 || input.get(0) == null) {
+ warn("Null input", PigWarning.UDF_WARNING_1);
+ return null;
+ }
+
+ if (inputSize != 4) {
+ throw new IOException("Stuff requires 4 arguments");
+ }
+
+ String inString = (String) input.get(0);
+
+ Integer startIndex = null;
+ Object inStartIndex = input.get(1);
+ //handle Double and Float
+ if(inStartIndex instanceof Number){
+ startIndex = ((Number)inStartIndex).intValue();
+ }else{
+ warn("Specified startIndex is of type " + inStartIndex.getClass().getName() + ", only Numbers are supported", PigWarning.UDF_WARNING_1);
+ return null;
+ }
+
+ Integer length = null;
+ Object inLength = input.get(2);
+
+ //handle Double and Float
+ if(inLength instanceof Number){
+ length = ((Number)inLength).intValue();
+ }else{
+ warn("Specified length is of type " + inLength.getClass().getName() + ", only Numbers are supported", PigWarning.UDF_WARNING_1);
+ return null;
+ }
+
+ String replacementString = (String) input.get(3);
+
+ int strLength = inString.length();
+ if (startIndex < 0 || startIndex >= strLength) {
+ throw new IOException("Given startIndex " + startIndex
+ + " is out of bounds: [0," + strLength + ")");
+ }
+
+ if (length < 0) {
+ throw new IOException(
+ "The number of characters to delete cannot be negative");
+ }
+
+ StringBuffer result = new StringBuffer();
+
+ int upperBound = (startIndex + length > strLength) ? strLength
+ : startIndex + length;
+
+ for (int i = 0; i < strLength;) {
+ // need to replace these characters
+ if (i >= startIndex && i < upperBound) {
+ if(replacementString != null)
+ result.append(replacementString);
+ i += length;
+ } else {
+ result.append(inString.charAt(i));
+ i++;
+ }
+ }
+
+ return result.toString();
+ }
+
+ /**
+ * @param input
+ * , schema of the input data
+ * @return output schema
+ */
+ @Override
+ public Schema outputSchema(Schema input) {
+ return new Schema(new Schema.FieldSchema(null, DataType.CHARARRAY));
+ }
+}
Added: pig/trunk/contrib/piggybank/java/src/test/java/org/apache/pig/piggybank/test/evaluation/string/TestStuff.java
URL: http://svn.apache.org/viewvc/pig/trunk/contrib/piggybank/java/src/test/java/org/apache/pig/piggybank/test/evaluation/string/TestStuff.java?rev=1564034&view=auto
==============================================================================
--- pig/trunk/contrib/piggybank/java/src/test/java/org/apache/pig/piggybank/test/evaluation/string/TestStuff.java (added)
+++ pig/trunk/contrib/piggybank/java/src/test/java/org/apache/pig/piggybank/test/evaluation/string/TestStuff.java Mon Feb 3 19:56:03 2014
@@ -0,0 +1,124 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.pig.piggybank.test.evaluation.string;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNull;
+
+import java.io.IOException;
+
+import org.apache.pig.data.Tuple;
+import org.apache.pig.data.TupleFactory;
+import org.apache.pig.piggybank.evaluation.string.Stuff;
+import org.junit.Test;
+
+public class TestStuff {
+
+ Stuff udf = new Stuff();
+
+ @Test
+ public void test() throws IOException {
+ Tuple tupleWithNullElement = TupleFactory.getInstance().newTuple(1);
+ String result = udf.exec(tupleWithNullElement);
+ assertNull(result);
+
+ Tuple t = TupleFactory.getInstance().newTuple(4);
+ t.set(0, "Chocolate Cake");
+ t.set(1, 10);
+ t.set(2, 4);
+ t.set(3, "Pie");
+ result = udf.exec(t);
+ assertEquals("Chocolate Pie", result);
+
+ t.set(0, "Old Zealand");
+ t.set(1, 0);
+ t.set(2, 3);
+ t.set(3, "New");
+ result = udf.exec(t);
+ assertEquals("New Zealand", result);
+
+ t.set(0, "Take a look");
+ t.set(1, 5);
+ t.set(2, 1);
+ t.set(3, "b");
+ result = udf.exec(t);
+ assertEquals("Take b look", result);
+
+ t.set(0, "Take a look");
+ t.set(1, 5);
+ t.set(2, 6);// replace until the end
+ t.set(3, "b");
+ result = udf.exec(t);
+ assertEquals("Take b", result);
+
+ t.set(0, "Take a look");
+ t.set(1, 4);
+ t.set(2, 7);// replace until the end
+ t.set(3, null);// delete the specified portion
+ result = udf.exec(t);
+ assertEquals("Take", result);
+
+ }
+
+ @Test(expected = IOException.class)
+ public void testArgumentCountMismatch() throws IOException {
+ Tuple t = TupleFactory.getInstance().newTuple(1);
+ t.set(0, "some_val");
+ udf.exec(t);
+ }
+
+ @Test(expected = IOException.class)
+ public void testIndexOutOfBounds() throws IOException {
+ Tuple t = TupleFactory.getInstance().newTuple(4);
+ t.set(0, "Replace me now!");
+ t.set(1, -1);
+ t.set(2, 2);
+ t.set(3, "test");
+ udf.exec(t);
+ }
+
+ @Test(expected = IOException.class)
+ public void testNegativeNumCharsToDelete() throws IOException {
+ Tuple t = TupleFactory.getInstance().newTuple(4);
+ t.set(0, "Replace me now!");
+ t.set(1, 0);
+ t.set(2, -2);
+ t.set(3, "test");
+ udf.exec(t);
+ }
+
+ @Test
+ public void testWithOtherTypes() throws IOException {
+ Tuple t = TupleFactory.getInstance().newTuple(4);
+ t.set(0, "Replace me now!");
+ t.set(1, new Double(8));
+ t.set(2, 2);
+ t.set(3, "ZZ");
+ String result = udf.exec(t);
+ assertEquals("Replace ZZ now!", result);
+
+ t = TupleFactory.getInstance().newTuple(4);
+ t.set(0, "Replace me now!");
+ t.set(1, new Float(14));
+ t.set(2, 1);
+ t.set(3, ";");
+ result = udf.exec(t);
+ assertEquals("Replace me now;", result);
+ }
+}