问:
when a JRadioButton is clicked it will not print out correct
i am trying to make a code that when pressed by he user it will print out correct but instead of printing out correct it just does nothing. i have researched this topic very clearly but i cannot seem to find the right answer if any body can help me it will be greatly appreciated</p>

```<code>import java.awt.FlowLayout;
import javax.swing.ButtonGroup;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JRadioButton;
import javax.swing.JOptionPane;

public class JRadioButtonTest
{

  public static void main(String[] args)
  {

    JFrame.setDefaultLookAndFeelDecorated(true);
    JFrame frame = new JFrame("JRadioButton Test");
    frame.setLayout(new FlowLayout());
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

    JRadioButton button1 = new JRadioButton("0.4");
    JRadioButton button2 = new JRadioButton("12");
    JRadioButton button3 = new JRadioButton("37");

    ButtonGroup colorButtonGroup = new ButtonGroup();
    colorButtonGroup.add(button1);
    colorButtonGroup.add(button2);
    colorButtonGroup.add(button3);

    frame.add(new JLabel("what is the density of a piece of rock that is 40 grams and 25cm3"));
    frame.add(button1);
    frame.add(button2);
    frame.add(button3);
    frame.pack();
    frame.setVisible(true);

    if(button2.isSelected()){
      JOptionPane.showMessageDialog(null,"correct");
      }
    }
  }
</code>```

答:
When you click on the radio button, it's an event happen at run time. The code you have at the end main method is executed ONLY once before the frame is loaded. In order to trigger that function every time you click, you need to register a listener. So, your code would look like this:

```<code>import java.awt.FlowLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.ButtonGroup;
    import javax.swing.JFrame;
    import javax.swing.JLabel;
    import javax.swing.JRadioButton;
    import javax.swing.JOptionPane;

    public class JRadioButtonTest
    {

      public static void main(String[] args)
      {

        JFrame.setDefaultLookAndFeelDecorated(true);
        JFrame frame = new JFrame("JRadioButton Test");
        frame.setLayout(new FlowLayout());
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        JRadioButton button1 = new JRadioButton("0.4");
        JRadioButton button2 = new JRadioButton("12");
        JRadioButton button3 = new JRadioButton("37");

        ButtonGroup colorButtonGroup = new ButtonGroup();
        colorButtonGroup.add(button1);
        colorButtonGroup.add(button2);
        colorButtonGroup.add(button3);

        frame.add(new JLabel("what is the density of a piece of rock that is 40 grams and 25cm3"));
        frame.add(button1);
        frame.add(button2);
        frame.add(button3);
        frame.pack();
        frame.setVisible(true);

        button2.addActionListener(new ActionListener() {

            @Override
            public void actionPerformed(ActionEvent e) {
                JOptionPane.showMessageDialog(null,"correct");

            }
        });
      }
    }
</code>```

Ideally, it's better to write your own implementation of ActionListener and register it to all the elements you need. You capture the element using the 'e' object.

Body:
i am trying to make a code that when pressed by he user it will print out correct but instead of printing out correct it just does nothing. i have researched this topic very clearly but i cannot seem to find the right answer if any body can help me it will be greatly appreciated

import java.awt.FlowLayout;
import javax.swing.ButtonGroup;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JRadioButton;
import javax.swing.JOptionPane;

public class JRadioButtonTest
{

  public static void main(String[] args)
  {

    JFrame.setDefaultLookAndFeelDecorated(true);
    JFrame frame = new JFrame("JRadioButton Test");
    frame.setLayout(new FlowLayout());
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

    JRadioButton button1 = new JRadioButton("0.4");
    JRadioButton button2 = new JRadioButton("12");
    JRadioButton button3 = new JRadioButton("37");

    ButtonGroup colorButtonGroup = new ButtonGroup();
    colorButtonGroup.add(button1);
    colorButtonGroup.add(button2);
    colorButtonGroup.add(button3);

    frame.add(new JLabel("what is the density of a piece of rock that is 40 grams and 25cm3"));
    frame.add(button1);
    frame.add(button2);
    frame.add(button3);
    frame.pack();
    frame.setVisible(true);

    if(button2.isSelected()){
      JOptionPane.showMessageDialog(null,"correct");
      }
    }
  }

Body:
When you click on the radio button, it's an event happen at run time. The code you have at the end main method is executed ONLY once before the frame is loaded. In order to trigger that function every time you click, you need to register a listener. So, your code would look like this:

import java.awt.FlowLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.ButtonGroup;
    import javax.swing.JFrame;
    import javax.swing.JLabel;
    import javax.swing.JRadioButton;
    import javax.swing.JOptionPane;

    public class JRadioButtonTest
    {

      public static void main(String[] args)
      {

        JFrame.setDefaultLookAndFeelDecorated(true);
        JFrame frame = new JFrame("JRadioButton Test");
        frame.setLayout(new FlowLayout());
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        JRadioButton button1 = new JRadioButton("0.4");
        JRadioButton button2 = new JRadioButton("12");
        JRadioButton button3 = new JRadioButton("37");

        ButtonGroup colorButtonGroup = new ButtonGroup();
        colorButtonGroup.add(button1);
        colorButtonGroup.add(button2);
        colorButtonGroup.add(button3);

        frame.add(new JLabel("what is the density of a piece of rock that is 40 grams and 25cm3"));
        frame.add(button1);
        frame.add(button2);
        frame.add(button3);
        frame.pack();
        frame.setVisible(true);

        button2.addActionListener(new ActionListener() {

            @Override
            public void actionPerformed(ActionEvent e) {
                JOptionPane.showMessageDialog(null,"correct");

            }
        });
      }
    }

Ideally, it's better to write your own implementation of ActionListener and register it to all the elements you need. You capture the element using the 'e' object.


来源: stackexchange

问:
Turn an Anaconda Python installation into a conda environment to be able to switch between different versions?
I need to use both Python 2.7, and 3.5. Ideally, I should use conda to create an alternative environment, but after using

bash Anaconda2-4.2.0-Linux-x86_64.sh

to install python 2.7, in a few minutes after downloading the shell script, then with

conda create -n py35 python=3.5 anaconda

always failed due to download time out, after more than dozen minutes of downloading numerous packages. (I'm in China, behind GFW.)

But I have no problem to install python 3.5 in a few minutes after downloading the shell script, by

bash Anaconda3-4.2.0-Linux-x86_64.sh

so I wonder if it's possible to manually turn the python 3.5 installation into a conda managed environment so that I can switch between them?

Thanks a lot for your help!

答:
set up shadowsocks client and proxchains4, I just set up an ubuntu server .

step1:
  buying or setting up a shadowsocks server

step2:
  install shadowsocks client

```<code>pip install shadowsocks
</code>```

step3:
    install proxychains

```<code>sudo apt-get install proxychains
</code>```

step4: setup and run setup
shadow socks client tutorial and
 proxychains tutorial

step5:
you can use proxychains to create new env

```<code>proxychains conda create -n py35 python=3.5
</code>```

ContentLicense: CC BY-SA 3.0

Body:
set up shadowsocks client and proxchains4, I just set up an ubuntu server .

step1:
  buying or setting up a shadowsocks server

step2:
  install shadowsocks client

pip install shadowsocks

step3:
    install proxychains

sudo apt-get install proxychains

step4: setup and run setup
shadow socks client tutorial and
 proxychains tutorial

step5:
you can use proxychains to create new env

proxychains conda create -n py35 python=3.5


问:
Convert milliseconds into UTC date object with UTC Time Zone
I am trying to convert milliseconds into UTC date object as below -

```<code>var tempDate = new Date(1465171200000);
// --> tempDate = Mon Jun 06 2016 05:30:00 **GMT+0530 (India Standard Time)** {}

var _utcDate = new Date(tempDate.getUTCFullYear(), tempDate.getUTCMonth(), tempDate.getUTCDate(),  tempDate.getUTCHours(), tempDate.getUTCMinutes(), tempDate.getUTCSeconds());
//--> _utcDate = Mon Jun 06 2016 00:00:00 **GMT+0530 (India Standard Time)** {}
</code>```

Time is resetting to UTC time but Time Zone is still coming as GMT+0530 (India Standard Time).
Is there any sure shot approach to convert milliseconds into UTC date object with UTC Time Zone?

答:
You say:

Time is resetting to UTC time but Time Zone is still coming as GMT+0530 (India Standard Time). Is there any sure shot approach to convert milliseconds into UTC date object with UTC Time Zone?

But I think you misunderstand what is occurring. When you pass a number to the Date constructor as in:

```<code>new Date(1465171200000)
</code>```

is it assumed to be milliseconds since the ECMAScript epoch (1970-01-01T00:00:00Z), so a Date object is created with that value as its internal time value. So Date objects are inherently UTC.

When you write that to a string, internally a human readable date string is generated based on the host timezone setting, which is why you see a date for  GMT+0530 (that is your host system timezone setting). The Date object itself does not have a timezone, it's always UTC.

When you then use UTC values to create a "local" Date using:

```<code>new Date(tempDate.getUTCFullYear(), tempDate.getUTCMonth(), ...)
</code>```

then the host timezone is used to generate a UTC time value equivalent to a "local" date for the associated values. You've effectively subtracted your timezone offset from the original time value so it now represents a different moment in time. You can get exactly the same result doing:

```<code>var d = new Date(1465171200000);
d.setMinutes(d.getMintues() + d.getTimezoneOffset());
</code>```

which just shows a bit more clearly what's going on. Note that ECMAScript timezone offsets are in minutes and have the opposite sense to UTC, that is, they are negative (-) for east and positive (+) for west. So an offset of UTC+05:30 it is represented as -330 and you need to add it to "shift" a Date rather than subtract it.

var tempDate = new Date(1465171200000);

var _utcDate = new Date(tempDate.getUTCFullYear(), tempDate.getUTCMonth(), tempDate.getUTCDate(),  tempDate.getUTCHours(), tempDate.getUTCMinutes(), tempDate.getUTCSeconds());

console.log('Direct conversion to Date\ntempDate: ' + tempDate.toString());
console.log('Adjusted using UTC methods\n_utcDate: ' + _utcDate.toString());

tempDate.setMinutes(tempDate.getMinutes() + tempDate.getTimezoneOffset());
console.log('Adjusted using timezoneOffset\ntempDate: ' + tempDate.toString());```

However, I can't understand why you want to do the above. 1465171200000 represents a specific moment in time (2016-06-06T00:00:00Z), adjusting it for every client timezone means it represents a different moment in time for each client with a different timezone offset.

Body:
I am trying to convert milliseconds into UTC date object as below -

var tempDate = new Date(1465171200000);
// --> tempDate = Mon Jun 06 2016 05:30:00 **GMT+0530 (India Standard Time)** {}

var _utcDate = new Date(tempDate.getUTCFullYear(), tempDate.getUTCMonth(), tempDate.getUTCDate(),  tempDate.getUTCHours(), tempDate.getUTCMinutes(), tempDate.getUTCSeconds());
//--> _utcDate = Mon Jun 06 2016 00:00:00 **GMT+0530 (India Standard Time)** {}

Time is resetting to UTC time but Time Zone is still coming as GMT+0530 (India Standard Time).
Is there any sure shot approach to convert milliseconds into UTC date object with UTC Time Zone?

Body:
You say:

Time is resetting to UTC time but Time Zone is still coming as GMT+0530 (India Standard Time). Is there any sure shot approach to convert milliseconds into UTC date object with UTC Time Zone?

But I think you misunderstand what is occurring. When you pass a number to the Date constructor as in:

new Date(1465171200000)

is it assumed to be milliseconds since the ECMAScript epoch (1970-01-01T00:00:00Z), so a Date object is created with that value as its internal time value. So Date objects are inherently UTC.

When you write that to a string, internally a human readable date string is generated based on the host timezone setting, which is why you see a date for  GMT+0530 (that is your host system timezone setting). The Date object itself does not have a timezone, it's always UTC.

When you then use UTC values to create a "local" Date using:

new Date(tempDate.getUTCFullYear(), tempDate.getUTCMonth(), ...)

then the host timezone is used to generate a UTC time value equivalent to a "local" date for the associated values. You've effectively subtracted your timezone offset from the original time value so it now represents a different moment in time. You can get exactly the same result doing:

var d = new Date(1465171200000);
d.setMinutes(d.getMintues() + d.getTimezoneOffset());

which just shows a bit more clearly what's going on. Note that ECMAScript timezone offsets are in minutes and have the opposite sense to UTC, that is, they are negative (-) for east and positive (+) for west. So an offset of UTC+05:30 it is represented as -330 and you need to add it to "shift" a Date rather than subtract it.

var tempDate = new Date(1465171200000);

var _utcDate = new Date(tempDate.getUTCFullYear(), tempDate.getUTCMonth(), tempDate.getUTCDate(),  tempDate.getUTCHours(), tempDate.getUTCMinutes(), tempDate.getUTCSeconds());

console.log('Direct conversion to Date\ntempDate: ' + tempDate.toString());
console.log('Adjusted using UTC methods\n_utcDate: ' + _utcDate.toString());

tempDate.setMinutes(tempDate.getMinutes() + tempDate.getTimezoneOffset());
console.log('Adjusted using timezoneOffset\ntempDate: ' + tempDate.toString());

However, I can't understand why you want to do the above. 1465171200000 represents a specific moment in time (2016-06-06T00:00:00Z), adjusting it for every client timezone means it represents a different moment in time for each client with a different timezone offset.


问:
How to remove user from list in AngularJS?
I have implemented a confirm button where the confirm button will remove a user from the list. But for some reason, it does not remove the user from the list. Can anyone check my js code to see what I have done wrong.

Here is my code

```<code>$scope.doDelete = function(user) {
    var index = $scope.userInfo.users.indexOf(user);
    $scope.userInfo.users.splice(index, 1);
    $window.location.href = '#/user';
}
</code>```

html

```<code><button class="delete" ng-click="doDelete(person)">Confirm</button>
</code>```

答:
You remove the item using:

```<code>$scope.userInfo.users.splice(index, 1);
</code>```

This only removes it in memory (this change isn't persisted). You then reload the page using:

```<code>$window.location.href = '#/user';
</code>```

So your array will be reset back to what it was before you removed the item.

Body:
I have implemented a confirm button where the confirm button will remove a user from the list. But for some reason, it does not remove the user from the list. Can anyone check my js code to see what I have done wrong.

Here is my code

$scope.doDelete = function(user) {
    var index = $scope.userInfo.users.indexOf(user);
    $scope.userInfo.users.splice(index, 1);
    $window.location.href = '#/user';
}

html

<button class="delete" ng-click="doDelete(person)">Confirm</button>

Body:
You remove the item using:

$scope.userInfo.users.splice(index, 1);

This only removes it in memory (this change isn't persisted). You then reload the page using:

$window.location.href = '#/user';

So your array will be reset back to what it was before you removed the item.


问:
Mapping a tuple
Is there a way to map a tuple?

Tried the following but not working

```<code>(a, b).map(v1,v2 => SomeFunction(v1, v2)
</code>```

Possible alternative is case class

```<code>      (a, b) match {
          case (Some(v1), Some(v2)) => SomeFunction(a, b)
          case _ => None
        }
</code>```

Wondering if there's other alternative.

答:
You can iterate over tuples and then map() over the Iterator ...

```<code>(9,'c',true).productIterator.map(???)
</code>```

... but tuples hold elements of differing types so the iterator is Iterator[Any] which isn't likely to be useful or safe.

Title: Mapping a tuple

Body:
Is there a way to map a tuple?

Tried the following but not working

(a, b).map(v1,v2 => SomeFunction(v1, v2)

Possible alternative is case class

      (a, b) match {
          case (Some(v1), Some(v2)) => SomeFunction(a, b)
          case _ => None
        }

Wondering if there's other alternative.

Body:
You can iterate over tuples and then map() over the Iterator ...

(9,'c',true).productIterator.map(???)

... but tuples hold elements of differing types so the iterator is Iterator[Any] which isn't likely to be useful or safe.


问:
Reset wireless adapter automatically
I have a windows 7 laptop that I am running continuously on wireless internet connect. But sometimes, there are problems with my wireless connection so I have to right click on the wireless connection icon and troubleshoot the problem. Is there a way I could automatically troubleshoot wireless problems with a batch file or windows task scheduler.

Regards

答:
Get devcon

Perform devcon find *

Copy USB\VID_****\PID_**** or PCI\VEN_****\DEV_**** (according BUS type) string for your wireless adapter

Create batch containing line: devcon restart "Your_copied_string"

Title: Reset wireless adapter automatically


问:
Deserializing a JSON Object with Gson TypeAdapter in an ordering-insensitive manner
Is it possible to achieve both of the following goals?

Be able to delegate to default Gson deserializer that invoked our custom implementation.

Be unaffected by different order of the keys in the JSON object

Below I describe two possible approaches that only achieve one of them.

The API I'm working with returns either a successful like:

```<code>{
  "type": "success",
  "data": {
    "display_name": "Invisible Pink Unicorn",
    "user_email": "user@example.com",
    "user_id": 1234
  }
}
</code>```

Or an error, like:

```<code>{
    "type": "error",
    "data": {
        "error_name": "incorrect_password",
        "error_message": "The username or password you entered is incorrect."
    }
}
</code>```

The way it's handled at the moment is by registering a TypeAdapter that throws an exception with the given "error_message" if the type is "error":

```<code>new GsonBuilder()
    .registerTypeAdapter(User.class, new ContentDeserializer<User>())
    .setFieldNamingPolicy(FieldNamingPolicy.LOWER_CASE_WITH_UNDERSCORES)
    .create()

public class ContentDeserializer<T> implements JsonDeserializer<T> {
    @Override
    public T deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context) throws JsonParseException {
        final JsonObject object = json.getAsJsonObject();
        final String type = object.get("type").getAsString();
        final JsonElement data = object.get("data");
        final Gson gson = new Gson();
        if ("error".equals(type)) {
            throw gson.fromJson(data, ApiError.class);
        } else {
            return gson.fromJson(data, typeOfT);
        }
    }
}
</code>```

Which is neat, because it's pretty succinct and uses a default deserializer to do all the hard work.

But actually it's wrong, because it doesn't use the same Gson to delegate that work to, so it will use a different field naming policy, for example.

To fix that, I wrote a TypeAdapterFactory:

```<code>public class UserAdapterFactory implements TypeAdapterFactory {

    @SuppressWarnings("unchecked")
    @Override
    public <T> TypeAdapter<T> create(Gson gson, TypeToken<T> type) {
        if (!User.class.isAssignableFrom(type.getRawType())) return null;
        final TypeAdapter<User> userAdapter = (TypeAdapter<User>) gson.getDelegateAdapter(this, type);
        final TypeAdapter<ApiError> apiErrorAdapter = gson.getAdapter(ApiError.class);
        return (TypeAdapter<T>) new Adapter(userAdapter, apiErrorAdapter);
    }

    private static class Adapter extends TypeAdapter<User> {
        private final TypeAdapter<User> userAdapter;
        private final TypeAdapter<ApiError> apiErrorAdapter;

        Adapter(TypeAdapter<User> userAdapter, TypeAdapter<ApiError> apiErrorAdapter) {
            this.userAdapter = userAdapter;
            this.apiErrorAdapter = apiErrorAdapter;
        }

        @Override
        public void write(JsonWriter out, User value) throws IOException {
        }

        @Override
        public User read(JsonReader in) throws IOException {
            User user = null;
            String type = null;
            in.beginObject();
            while (in.hasNext()) {
                switch (in.nextName()) {
                    case "type":
                        type = in.nextString();
                        break;
                    case "data":
                        if ("error".equals(type)) {
                            throw apiErrorAdapter.read(in);
                        } else if ("success".equals(type)) {
                            user = userAdapter.read(in);
                        }
                        break;
                }
            }
            in.endObject();
            return user;
        }
    }
}
</code>```

Which was a lot more work, but at least lets me delegate to the same Gson configuration.

The problem with this approach is that it breaks when the JSON Object will have a different order:

```<code>{
  "data": {
    "display_name": "Invisible Pink Unicorn",
    "user_email": "user@example.com",
    "user_id": 1234
  },
  "type": "success"
}
</code>```

And I don't see any way around this, because I don't think JsonReader has an option to read the input twice, there's also no way to cache the "data" value in an abstract type like JsonElement to parse after "type" has been encountered.

答:
But actually it's wrong, because it doesn't use the same Gson to delegate that work to, so it will use a different field naming policy, for example.

Correct. You should use JsonDeserializationContext.

... because I don't think JsonReader has an option to read the input twice, there's also no way to cache the "data" value in an abstract type like JsonElement to parse after "type" has been encountered.

Correct. JsonReader is a stream reader whilst JsonElement is a tree. These are like SAX and DOM from the XML world with all of their respective pros and cons. Streaming readers just read input stream, and you have to buffer/cache intermediate data yourself.

You can use both approaches for you case, but I would go with JsonDeserializer for its simplicity (assuming you're not going to write a super-fast deserializer).

I'm not really sure how your User and ApiError relate to each other, but I would go with a common class for both two different kinds of values: real values and errors. It looks like your two classes have a common parent or ancestor, but I'm not really sure how you deal with them at a call-site (perhaps instanceof?). Say, something like this (constructor hidden in order to encapsulate the complexity of the object structure initialization):

final class Content<T> {

    private final boolean isSuccess;
    private final T data;
    private final ApiError error;

    private Content(final boolean isSuccess, final T data, final ApiError error) {
        this.isSuccess = isSuccess;
        this.data = data;
        this.error = error;
    }

    static <T> Content<T> success(final T data) {
        return new Content<>(true, data, null);
    }

    static <T> Content<T> error(final ApiError error) {
        return new Content<>(false, null, error);
    }

    boolean isSuccess() {
        return isSuccess;
    }

    T getData()
            throws IllegalStateException {
        if ( !isSuccess ) {
            throw new IllegalStateException();
        }
        return data;
    }

    ApiError getError()
            throws IllegalStateException {
        if ( isSuccess ) {
            throw new IllegalStateException();
        }
        return error;
    }

}
```

<p>And both <code>User</code> and <code>ApiError</code> from my perspective (I prefer <code>@SerializedName</code> though to have a stronger control over naming -- but it seems like a matter of habit).</p>

<pre class="lang-java prettyprint-override"><code>final class ApiError {

    @SuppressWarnings("error_name")
    final String errorName = null;

    @SerializedName("error_message")
    final String errorMessage = null;

}
</code>```

final class User {

    @SerializedName("display_name")
    final String displayName = null;

    @SerializedName("user_email")
    final String userEmail = null;

    @SuppressWarnings("user_id")
    final int userId = Integer.valueOf(0);

}
```

<p>Next, since tree manipulation is easier, just implement your JSON deserializer:</p>

<pre class="lang-java prettyprint-override"><code>final class ContentJsonDeserializer<T>
        implements JsonDeserializer<Content<T>> {

    // This deserializer holds no state
    private static final JsonDeserializer<?> contentJsonDeserializer = new ContentJsonDeserializer<>();

    private ContentJsonDeserializer() {
    }

    // ... and we hide away that fact not letting this one to be instantiated at call sites
    static <T> JsonDeserializer<T> getContentJsonDeserializer() {
        // Narrowing down the @SuppressWarnings scope -- suppressing warnings for entire method may be harmful
        @SuppressWarnings("unchecked")
        final JsonDeserializer<T> contentJsonDeserializer = (JsonDeserializer<T>) ContentJsonDeserializer.contentJsonDeserializer;
        return contentJsonDeserializer;
    }

    @Override
    public Content<T> deserialize(final JsonElement jsonElement, final Type type, final JsonDeserializationContext context)
            throws JsonParseException {
        final JsonObject jsonObject = jsonElement.getAsJsonObject();
        final String responseType = jsonObject.getAsJsonPrimitive("type").getAsString();
        switch ( responseType ) {
        case "success":
            return success(context.deserialize(jsonObject.get("data"), getTypeParameter0(type)));
        case "error":
            return error(context.deserialize(jsonObject.get("data"), ApiError.class));
        default:
            throw new JsonParseException(responseType);
        }
    }

    // Trying to detect any given type parameterization for its first type parameter
    private static Type getTypeParameter0(final Type type) {
        if ( !(type instanceof ParameterizedType) ) {
            return Object.class;
        }
        return ((ParameterizedType) type).getActualTypeArguments()[0];
    }

}
</code>```

Demo:

```<code>private static final Gson gson = new GsonBuilder()
        .registerTypeAdapter(Content.class, getContentJsonDeserializer())
        .create();

private static final Type userContent = new TypeToken<Content<User>>() {
}.getType();

public static void main(final String... args)
        throws IOException {
    for ( final String name : ImmutableList.of("success.json", "error.json", "success-reversed.json", "error-reversed.json") ) {
        try ( final JsonReader jsonReader = getPackageResourceJsonReader(Q44400163.class, name) ) {
            final Content<User> content = gson.fromJson(jsonReader, userContent);
            if ( content.isSuccess() ) {
                System.out.println("SUCCESS: " + content.getData().displayName);
            } else {
                System.out.println("ERROR:   " + content.getError().errorMessage);
            }
        }
    }
}
</code>```

Output:

SUCCESS: Invisible Pink Unicorn

  ERROR:   The username or password you entered is incorrect.

  SUCCESS: Invisible Pink Unicorn

  ERROR:   The username or password you entered is incorrect.

Now, back to you original question regarding TypeAdapter. As I mentioned above, you can do it using a type adapter as well, but you have to implement the two cases support:

Forward case, and you have already implemented it (the best case): read the type property first, and then read the data property according to your real date type. By the way, your TypeAdapter implementation is far from being generic: you had to resolve the real data type and its adapter using Gson.getDelegateAdapter.

Reverse case (the worst case): read the data property into a tree view (therefore buffering it into memory) as a JsonElement instance (you have to get the TypeAdapter<JsonElement> from the Gson instance in the create method first), and then, according to the next type property value, read it as a value from the tree using TypeAdapter.fromJsonTree.

And yes, don't forget to check the parsing state here (handle missing type and data for both cases somehow). As you can see, this introduces variable complexity and performance/memory cost, but it can give you the best performance. You decide.

Body:
Is it possible to achieve both of the following goals?

Be able to delegate to default Gson deserializer that invoked our custom implementation.

Be unaffected by different order of the keys in the JSON object

Below I describe two possible approaches that only achieve one of them.

The API I'm working with returns either a successful like:

{
  "type": "success",
  "data": {
    "display_name": "Invisible Pink Unicorn",
    "user_email": "user@example.com",
    "user_id": 1234
  }
}

Or an error, like:

{
    "type": "error",
    "data": {
        "error_name": "incorrect_password",
        "error_message": "The username or password you entered is incorrect."
    }
}

The way it's handled at the moment is by registering a TypeAdapter that throws an exception with the given "error_message" if the type is "error":

new GsonBuilder()
    .registerTypeAdapter(User.class, new ContentDeserializer<User>())
    .setFieldNamingPolicy(FieldNamingPolicy.LOWER_CASE_WITH_UNDERSCORES)
    .create()

public class ContentDeserializer<T> implements JsonDeserializer<T> {
    @Override
    public T deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context) throws JsonParseException {
        final JsonObject object = json.getAsJsonObject();
        final String type = object.get("type").getAsString();
        final JsonElement data = object.get("data");
        final Gson gson = new Gson();
        if ("error".equals(type)) {
            throw gson.fromJson(data, ApiError.class);
        } else {
            return gson.fromJson(data, typeOfT);
        }
    }
}

Which is neat, because it's pretty succinct and uses a default deserializer to do all the hard work.

But actually it's wrong, because it doesn't use the same Gson to delegate that work to, so it will use a different field naming policy, for example.

To fix that, I wrote a TypeAdapterFactory:

public class UserAdapterFactory implements TypeAdapterFactory {

    @SuppressWarnings("unchecked")
    @Override
    public <T> TypeAdapter<T> create(Gson gson, TypeToken<T> type) {
        if (!User.class.isAssignableFrom(type.getRawType())) return null;
        final TypeAdapter<User> userAdapter = (TypeAdapter<User>) gson.getDelegateAdapter(this, type);
        final TypeAdapter<ApiError> apiErrorAdapter = gson.getAdapter(ApiError.class);
        return (TypeAdapter<T>) new Adapter(userAdapter, apiErrorAdapter);
    }

    private static class Adapter extends TypeAdapter<User> {
        private final TypeAdapter<User> userAdapter;
        private final TypeAdapter<ApiError> apiErrorAdapter;

        Adapter(TypeAdapter<User> userAdapter, TypeAdapter<ApiError> apiErrorAdapter) {
            this.userAdapter = userAdapter;
            this.apiErrorAdapter = apiErrorAdapter;
        }

        @Override
        public void write(JsonWriter out, User value) throws IOException {
        }

        @Override
        public User read(JsonReader in) throws IOException {
            User user = null;
            String type = null;
            in.beginObject();
            while (in.hasNext()) {
                switch (in.nextName()) {
                    case "type":
                        type = in.nextString();
                        break;
                    case "data":
                        if ("error".equals(type)) {
                            throw apiErrorAdapter.read(in);
                        } else if ("success".equals(type)) {
                            user = userAdapter.read(in);
                        }
                        break;
                }
            }
            in.endObject();
            return user;
        }
    }
}

Which was a lot more work, but at least lets me delegate to the same Gson configuration.

The problem with this approach is that it breaks when the JSON Object will have a different order:

{
  "data": {
    "display_name": "Invisible Pink Unicorn",
    "user_email": "user@example.com",
    "user_id": 1234
  },
  "type": "success"
}

And I don't see any way around this, because I don't think JsonReader has an option to read the input twice, there's also no way to cache the "data" value in an abstract type like JsonElement to parse after "type" has been encountered.

Body:
But actually it's wrong, because it doesn't use the same Gson to delegate that work to, so it will use a different field naming policy, for example.

Correct. You should use JsonDeserializationContext.

... because I don't think JsonReader has an option to read the input twice, there's also no way to cache the "data" value in an abstract type like JsonElement to parse after "type" has been encountered.

Correct. JsonReader is a stream reader whilst JsonElement is a tree. These are like SAX and DOM from the XML world with all of their respective pros and cons. Streaming readers just read input stream, and you have to buffer/cache intermediate data yourself.

You can use both approaches for you case, but I would go with JsonDeserializer for its simplicity (assuming you're not going to write a super-fast deserializer).

I'm not really sure how your User and ApiError relate to each other, but I would go with a common class for both two different kinds of values: real values and errors. It looks like your two classes have a common parent or ancestor, but I'm not really sure how you deal with them at a call-site (perhaps instanceof?). Say, something like this (constructor hidden in order to encapsulate the complexity of the object structure initialization):

final class Content<T> {

    private final boolean isSuccess;
    private final T data;
    private final ApiError error;

    private Content(final boolean isSuccess, final T data, final ApiError error) {
        this.isSuccess = isSuccess;
        this.data = data;
        this.error = error;
    }

    static <T> Content<T> success(final T data) {
        return new Content<>(true, data, null);
    }

    static <T> Content<T> error(final ApiError error) {
        return new Content<>(false, null, error);
    }

    boolean isSuccess() {
        return isSuccess;
    }

    T getData()
            throws IllegalStateException {
        if ( !isSuccess ) {
            throw new IllegalStateException();
        }
        return data;
    }

    ApiError getError()
            throws IllegalStateException {
        if ( isSuccess ) {
            throw new IllegalStateException();
        }
        return error;
    }

}

And both User and ApiError from my perspective (I prefer @SerializedName though to have a stronger control over naming -- but it seems like a matter of habit).

final class ApiError {

    @SuppressWarnings("error_name")
    final String errorName = null;

    @SerializedName("error_message")
    final String errorMessage = null;

}

final class User {

    @SerializedName("display_name")
    final String displayName = null;

    @SerializedName("user_email")
    final String userEmail = null;

    @SuppressWarnings("user_id")
    final int userId = Integer.valueOf(0);

}

Next, since tree manipulation is easier, just implement your JSON deserializer:

final class ContentJsonDeserializer<T>
        implements JsonDeserializer<Content<T>> {

    // This deserializer holds no state
    private static final JsonDeserializer<?> contentJsonDeserializer = new ContentJsonDeserializer<>();

    private ContentJsonDeserializer() {
    }

    // ... and we hide away that fact not letting this one to be instantiated at call sites
    static <T> JsonDeserializer<T> getContentJsonDeserializer() {
        // Narrowing down the @SuppressWarnings scope -- suppressing warnings for entire method may be harmful
        @SuppressWarnings("unchecked")
        final JsonDeserializer<T> contentJsonDeserializer = (JsonDeserializer<T>) ContentJsonDeserializer.contentJsonDeserializer;
        return contentJsonDeserializer;
    }

    @Override
    public Content<T> deserialize(final JsonElement jsonElement, final Type type, final JsonDeserializationContext context)
            throws JsonParseException {
        final JsonObject jsonObject = jsonElement.getAsJsonObject();
        final String responseType = jsonObject.getAsJsonPrimitive("type").getAsString();
        switch ( responseType ) {
        case "success":
            return success(context.deserialize(jsonObject.get("data"), getTypeParameter0(type)));
        case "error":
            return error(context.deserialize(jsonObject.get("data"), ApiError.class));
        default:
            throw new JsonParseException(responseType);
        }
    }

    // Trying to detect any given type parameterization for its first type parameter
    private static Type getTypeParameter0(final Type type) {
        if ( !(type instanceof ParameterizedType) ) {
            return Object.class;
        }
        return ((ParameterizedType) type).getActualTypeArguments()[0];
    }

}

Demo:

private static final Gson gson = new GsonBuilder()
        .registerTypeAdapter(Content.class, getContentJsonDeserializer())
        .create();

private static final Type userContent = new TypeToken<Content<User>>() {
}.getType();

public static void main(final String... args)
        throws IOException {
    for ( final String name : ImmutableList.of("success.json", "error.json", "success-reversed.json", "error-reversed.json") ) {
        try ( final JsonReader jsonReader = getPackageResourceJsonReader(Q44400163.class, name) ) {
            final Content<User> content = gson.fromJson(jsonReader, userContent);
            if ( content.isSuccess() ) {
                System.out.println("SUCCESS: " + content.getData().displayName);
            } else {
                System.out.println("ERROR:   " + content.getError().errorMessage);
            }
        }
    }
}

Output:

SUCCESS: Invisible Pink Unicorn

  ERROR:   The username or password you entered is incorrect.

  SUCCESS: Invisible Pink Unicorn

  ERROR:   The username or password you entered is incorrect.

Now, back to you original question regarding TypeAdapter. As I mentioned above, you can do it using a type adapter as well, but you have to implement the two cases support:

Forward case, and you have already implemented it (the best case): read the type property first, and then read the data property according to your real date type. By the way, your TypeAdapter implementation is far from being generic: you had to resolve the real data type and its adapter using Gson.getDelegateAdapter.

Reverse case (the worst case): read the data property into a tree view (therefore buffering it into memory) as a JsonElement instance (you have to get the TypeAdapter<JsonElement> from the Gson instance in the create method first), and then, according to the next type property value, read it as a value from the tree using TypeAdapter.fromJsonTree.

And yes, don't forget to check the parsing state here (handle missing type and data for both cases somehow). As you can see, this introduces variable complexity and performance/memory cost, but it can give you the best performance. You decide.


问:
Android scaling down image from gallery with Uri and Bitmap
I am receiving a FileNotFound exception when trying to turn an image into a Bitmap to scale the image down significantly.

I am retrieving an image the user selects from the gallery like so

```<code>public static void GET_PICTURE_FROM_GALLERY (Activity activity)
{
    Intent getIntent = new Intent(Intent.ACTION_GET_CONTENT);
    getIntent.setType("image/*");

    Intent pickIntent = new Intent(Intent.ACTION_PICK, android.provider.MediaStore.Images.Media.EXTERNAL_CONTENT_URI);
    pickIntent.setType("image/*");

    Intent chooserIntent = Intent.createChooser(getIntent, "Select Image");
    chooserIntent.putExtra(Intent.EXTRA_INITIAL_INTENTS, new Intent[] {pickIntent});

    activity.startActivityForResult(chooserIntent, REQUEST_SELECT_PHOTO);
}
</code>```

Then, when the user is done picking:

```<code>public void setChosenPicture (Activity activity, Intent data)
{
    if(editingViewHelper != null)
    {
        String[] filePathColumn = {MediaStore.Images.Media.DATA};

        Uri selectedImage = data.getData();

        System.out.println("GOT URI: " + selectedImage.toString());

        Cursor cursor = activity.getContentResolver().query(selectedImage, filePathColumn, null, null, null);
        cursor.moveToFirst();

        int columnIndex = cursor.getColumnIndex(filePathColumn[0]);
        editingViewHelper.holder.tempUri = Uri.parse(cursor.getString(columnIndex));

        System.out.println("SET URI: " + editingViewHelper.holder.tempUri.toString());

        cursor.close();

        editingViewHelper.holder.imageView.setImageURI(editingViewHelper.holder.tempUri);
    }
}
</code>```

This outputs the following:

```<code>GOT URI: content://media/external/images/media/110
SET URI: /storage/emulated/0/DIRECTORY/IMG_20170606_154512_1664512804.jpg
</code>```

Now this works great, but only if I call imageView.setImageUri(uri); However, I cannot do that because I must scale the image down so the app doesn't use ridiculous amounts of ram. To do this, I have this method

```<code>public static Bitmap decodeUri(Context c, Uri uri, final int requiredSize)
{
    System.out.println("URI: " + uri.toString());

    try
    {
        BitmapFactory.Options o = new BitmapFactory.Options();
        o.inJustDecodeBounds = true;

 //This line is where the error occurs.
     BitmapFactory.decodeStream(c.getContentResolver().openInputStream(uri), null, o);

        int width_tmp = o.outWidth;
        int height_tmp = o.outHeight;
        int scale = 1;

        while(true)
        {
            if(width_tmp / 2 < requiredSize || height_tmp / 2 < requiredSize)
                break;

            width_tmp /= 2;
            height_tmp /= 2;
            scale *= 2;
        }

        BitmapFactory.Options o2 = new BitmapFactory.Options();
        o2.inSampleSize = scale;

        return BitmapFactory.decodeStream(c.getContentResolver().openInputStream(uri), null, o2);
    }
    catch (FileNotFoundException e)
    {
        e.printStackTrace();
        return null;
    }
}
</code>```

And finally, I have the following .output FileNotFound exception

```<code>URI: /storage/emulated/0/DIRECTORY/IMG_20170606_154512_1664512804.jpg
java.io.FileNotFoundException: No content provider: /storage/emulated/0/DIRECTORY/IMG_20170606_154512_1664512804.jpg
</code>```

Now the weird thing is that this method does work but only if it is passed the Uri from a picture taken in my app. Here is an example output of the last method that does not throw any errors

```<code>Uri: content://com.subliroid.dinnerdecider.provider/external_files/Pictures/DIRECTORY/IMG_20170606_154512_1664512804.jpg
</code>```

I am able to call imageView.setImageUri(uri) with BOTH types of uris, but I cannot scale the one type down. I was able to ignore this until I began testing my app on real devices that take 4k+ pictures compared to the small ones the emulator takes.

答:
The simplest thing to do, by far, is to delete most of this code and use an existing image-loading library. Google recommends Glide; I have used Picasso, and there are plenty of others.

Then, when the user is done picking:

The query() call will fail in many situations (images on removable storage, users choosing apps that you might not expect in response to your Intent, etc.).

And finally, I have the following .output FileNotFound exception

You are unnecessarily creating a new Uri, and you are doing so incorrectly, as the value you are passing into Uri.parse() does not have a scheme.

If you are not going to use existing, already-debugged code (i.e., image-loading libraries), pass in the Uri you were given in onActivityResult() to your bitmap-scaling code. Then, figure out when you are going to move most of this logic off of the main application thread, as you are freezing your UI in your current implementation.

Body:
I am receiving a FileNotFound exception when trying to turn an image into a Bitmap to scale the image down significantly.

I am retrieving an image the user selects from the gallery like so

public static void GET_PICTURE_FROM_GALLERY (Activity activity)
{
    Intent getIntent = new Intent(Intent.ACTION_GET_CONTENT);
    getIntent.setType("image/*");

    Intent pickIntent = new Intent(Intent.ACTION_PICK, android.provider.MediaStore.Images.Media.EXTERNAL_CONTENT_URI);
    pickIntent.setType("image/*");

    Intent chooserIntent = Intent.createChooser(getIntent, "Select Image");
    chooserIntent.putExtra(Intent.EXTRA_INITIAL_INTENTS, new Intent[] {pickIntent});

    activity.startActivityForResult(chooserIntent, REQUEST_SELECT_PHOTO);
}

Then, when the user is done picking:

public void setChosenPicture (Activity activity, Intent data)
{
    if(editingViewHelper != null)
    {
        String[] filePathColumn = {MediaStore.Images.Media.DATA};

        Uri selectedImage = data.getData();

        System.out.println("GOT URI: " + selectedImage.toString());

        Cursor cursor = activity.getContentResolver().query(selectedImage, filePathColumn, null, null, null);
        cursor.moveToFirst();

        int columnIndex = cursor.getColumnIndex(filePathColumn[0]);
        editingViewHelper.holder.tempUri = Uri.parse(cursor.getString(columnIndex));

        System.out.println("SET URI: " + editingViewHelper.holder.tempUri.toString());

        cursor.close();

        editingViewHelper.holder.imageView.setImageURI(editingViewHelper.holder.tempUri);
    }
}

This outputs the following:

GOT URI: content://media/external/images/media/110
SET URI: /storage/emulated/0/DIRECTORY/IMG_20170606_154512_1664512804.jpg

Now this works great, but only if I call imageView.setImageUri(uri); However, I cannot do that because I must scale the image down so the app doesn't use ridiculous amounts of ram. To do this, I have this method

public static Bitmap decodeUri(Context c, Uri uri, final int requiredSize)
{
    System.out.println("URI: " + uri.toString());

    try
    {
        BitmapFactory.Options o = new BitmapFactory.Options();
        o.inJustDecodeBounds = true;

 //This line is where the error occurs.
     BitmapFactory.decodeStream(c.getContentResolver().openInputStream(uri), null, o);

        int width_tmp = o.outWidth;
        int height_tmp = o.outHeight;
        int scale = 1;

        while(true)
        {
            if(width_tmp / 2 < requiredSize || height_tmp / 2 < requiredSize)
                break;

            width_tmp /= 2;
            height_tmp /= 2;
            scale *= 2;
        }

        BitmapFactory.Options o2 = new BitmapFactory.Options();
        o2.inSampleSize = scale;

        return BitmapFactory.decodeStream(c.getContentResolver().openInputStream(uri), null, o2);
    }
    catch (FileNotFoundException e)
    {
        e.printStackTrace();
        return null;
    }
}

And finally, I have the following .output FileNotFound exception

URI: /storage/emulated/0/DIRECTORY/IMG_20170606_154512_1664512804.jpg
java.io.FileNotFoundException: No content provider: /storage/emulated/0/DIRECTORY/IMG_20170606_154512_1664512804.jpg

Now the weird thing is that this method does work but only if it is passed the Uri from a picture taken in my app. Here is an example output of the last method that does not throw any errors

Uri: content://com.subliroid.dinnerdecider.provider/external_files/Pictures/DIRECTORY/IMG_20170606_154512_1664512804.jpg

I am able to call imageView.setImageUri(uri) with BOTH types of uris, but I cannot scale the one type down. I was able to ignore this until I began testing my app on real devices that take 4k+ pictures compared to the small ones the emulator takes.


问:
Replacing DBMS_OUPUT in a PL/SQL test LOOP to return a collection
So I have this assignment where I have to create a stored procedure to search for movies in an Oracle DataBase.

The search string follow the following logic :

It looks for the year of the movie in parenthesis

Ex. (1992)

It looks for a range of year in brackets

Ex. [1992,2000]

It looks for a word contained in the title, country, realisator, genre, actors or scenarists.

Any of the above can be combined multiple times.

Ex. : The Lord Of the Ring Ian McKellen Christopher Lee [1992,2000]

The logic used to solve this problem was to make a giant query to group all the required data then use a cursor to loop through the result set with a cursor to check if every word of the search string is valid.

I managed to make a procedure that works as expected, but the only way I found to return the results was to use DBMS_OUTPUT. Now the problem is that when I plug this is Hibernate the DBMS_OUTPUT is not sent over to the client. I've read some way to force the output by setting DBMS_OUTPUT.enable, but I feel that this is not the proper way to do it.

So here are my questions :

Is my logic flawed? Is there a simpler way to archive this with a single select or something?

Is there a way to dynamically push data inside a cursor and return it?

Am I really supposed to trick the DBMS_OUTPUT so it is sent over to hibernate?

Here's my code :

```<code>CREATE OR REPLACE PROCEDURE p_SearchFilm(searchString IN VARCHAR2) IS
    IsValid BOOLEAN;
    y1 INTEGER;
    y2 INTEGER;
    subStrArray apex_application_global.vc_arr2;
    term VARCHAR(100);

    CURSOR films IS
            Select FilmId, Titre, real.Prenom||' '||real.nom as Realisateur, anneeSortie, ListPays, ListGenres,
                   ListScenaristes, ListActeurs, langueOrigine
                from Film
                natural left join
                    (select FilmId, listagg(p.Nom, ',') within group (Order By p.nom) ListPays from Film
                        natural join Film_vs_pays
                        natural join Pays p
                        Group by FilmId)
                natural left join
                    (select FilmId, listagg(g.Nom, ',') within group (Order By g.nom) ListGenres from Film
                        natural join Film_vs_Genre
                        natural join Genre g
                        Group by FilmId)
                natural left join
                    (select FilmId, listagg(p.Prenom||' '||p.Nom, ',') within group (Order By p.nom) ListScenaristes from Film
                        natural join Scenariste s
                        join Personne p on s.personneId = p.personneId
                        Group by FilmId)
                natural left join
                    (select FilmId, listagg(p.Prenom||' '||p.Nom, ',') within group (Order By p.nom) ListActeurs from Film
                        natural join Personnage perso
                        join Personne p on perso.personneId = p.personneId
                        Group by FilmId)
                left join Personne real on real.personneId = realisateurId;
BEGIN
    <<FILM_LOOP>>
    FOR film IN films LOOP
        subStrArray := apex_util.string_to_table(searchString, ' ');
        FOR i in 1..subStrArray.count LOOP
            IsValid:= FALSE;
            term:= subStrArray(i);
            IF REGEXP_LIKE(term, '\(\d{4}\)') THEN
                IF film.anneeSortie = TO_NUMBER(regexp_substr(term, '\d{4}')) THEN
                    IsValid:= TRUE;
                END IF;
            ELSIF REGEXP_LIKE(term, '\[\d{4},\d{4}\]') THEN
                y1:= regexp_substr(term, '\d{4}', 1, 1);
                y2:= regexp_substr(term, '\d{4}', 1, 2);

                IF film.anneeSortie BETWEEN y1 AND y2 THEN
                    IsValid:= TRUE;
                END IF;
            ELSE
                IF UPPER(film.Titre||film.Realisateur||film.ListActeurs||film.ListScenaristes||film.ListGenres||film.ListPays||film.langueOrigine)
                     LIKE '%'||UPPER(term)||'%' THEN
                    IsValid:= TRUE;
                END IF;
            END IF;

            IF NOT IsValid THEN
                CONTINUE FILM_LOOP;
            END IF;

        END LOOP;

        DBMS_OUTPUT.put_line(film.FilmId||'|'||film.Titre);
    END LOOP;
END;
</code>```

A small disclaimer here :

I saw some similar questions that addressed this issue, but the ones that used cursors were returning a complete select, not hand picked rows.

The question about DBMS_OUTPUT and Hibernate stated that it should be avoided.

The questions using piped rows seamed to work only with functions (Changing the procedure for a function called by the procedure could be a valid work around, I'd like to know if something else is possible before tho).

答:
The first part of this can probably be accomplished with just a query. You can define your search terms like this: How to declare variable and use it in the same SQL script? (Oracle SQL)

I'll leave the basic query writing to you (e.g. joining appropriate data), but your script will in effect look something like this:

```<code>DEFINE var_year1 = 1992;
DEFINE var_year2 = 1994;
DEFINE var_country = null;
DEFINE var_title = 'Lord Of The Rings';
DEFINE var_realisator = null;
DEFINE var_genre = null;
DEFINE var_actors = 'Ian';
DEFINE var_scenarists = 'Lee';

SELECT film_id, title, year
FROM ...
WHERE year BETWEEN &var_year1 AND &var_year2
 AND UPPER(title) LIKE UPPER('%&var_title%')
 AND UPPER(country) LIKE UPPER('%&var_country%')
 AND UPPER(realisator) LIKE UPPER('%&var_realisator%')
 AND UPPER(genre) LIKE UPPER('%&var_genre%')
 AND UPPER(actors) LIKE UPPER('%&var_actors%')
 AND UPPER(scenarists) LIKE UPPER('%&var_scenarists%');
/
</code>```

The reason I only select film_id, title, and year is because the title and year will be distinct values to the film_id. There are a couple of ways to skin this cat, but it all revolves around using a LIKE statement with variables that you have defined. If you do not want to explicitly define the values in the script, you can use the ACCEPT command. Or, you can interface it with something else that applies those values into the variables.

With this approach, it was kind of a shot in the dark on how you really have your data laid out. But keep in mind good relational database management practices, and you should be able to turn this into a useable query.

Additional Method:

You can also use a series of subqueries to find the same data above using the like statements, then INNER JOIN them together to figure out which ones are in common. Example:

```<code>WITH sub_title AS (SELECT film_id FROM Film WHERE UPPER(title) LIKE UPPER('%&var_title%')),
...
sub_actor AS (SELECT film_id FROM (...) WHERE UPPER(actor) LIKE UPPER('%&var_actor%'))
SELECT film_id
FROM sub_title t
     INNER JOIN sub_actor a ON a.film_id = t.film_id;
/
</code>```

If you had searched for 'star war' in that, you would have returned for example

```<code>1   Star Wars A New Hope
2   Star Wars The Empire Strikes Back
3   Star Wars Return of the Jedi
</code>```

Then in the second subquery if you had searched 'Donald Glover' you would have gotten

```<code>2   Star Wars The Empire Strikes Back
3   Star Wars Return of the Jedi
</code>```

Then, the INNER JOIN would have given you ID numbers 2 and 3 because those were the only ones where all of the criteria were met. Repeat the process for your other search terms. I hope this helps.

Body:
So I have this assignment where I have to create a stored procedure to search for movies in an Oracle DataBase.

The search string follow the following logic :

It looks for the year of the movie in parenthesis

Ex. (1992)

It looks for a range of year in brackets

Ex. [1992,2000]

It looks for a word contained in the title, country, realisator, genre, actors or scenarists.

Any of the above can be combined multiple times.

Ex. : The Lord Of the Ring Ian McKellen Christopher Lee [1992,2000]

The logic used to solve this problem was to make a giant query to group all the required data then use a cursor to loop through the result set with a cursor to check if every word of the search string is valid.

I managed to make a procedure that works as expected, but the only way I found to return the results was to use DBMS_OUTPUT. Now the problem is that when I plug this is Hibernate the DBMS_OUTPUT is not sent over to the client. I've read some way to force the output by setting DBMS_OUTPUT.enable, but I feel that this is not the proper way to do it.

So here are my questions :

Is my logic flawed? Is there a simpler way to archive this with a single select or something?

Is there a way to dynamically push data inside a cursor and return it?

Am I really supposed to trick the DBMS_OUTPUT so it is sent over to hibernate?

Here's my code :

CREATE OR REPLACE PROCEDURE p_SearchFilm(searchString IN VARCHAR2) IS
    IsValid BOOLEAN;
    y1 INTEGER;
    y2 INTEGER;
    subStrArray apex_application_global.vc_arr2;
    term VARCHAR(100);

    CURSOR films IS
            Select FilmId, Titre, real.Prenom||' '||real.nom as Realisateur, anneeSortie, ListPays, ListGenres,
                   ListScenaristes, ListActeurs, langueOrigine
                from Film
                natural left join
                    (select FilmId, listagg(p.Nom, ',') within group (Order By p.nom) ListPays from Film
                        natural join Film_vs_pays
                        natural join Pays p
                        Group by FilmId)
                natural left join
                    (select FilmId, listagg(g.Nom, ',') within group (Order By g.nom) ListGenres from Film
                        natural join Film_vs_Genre
                        natural join Genre g
                        Group by FilmId)
                natural left join
                    (select FilmId, listagg(p.Prenom||' '||p.Nom, ',') within group (Order By p.nom) ListScenaristes from Film
                        natural join Scenariste s
                        join Personne p on s.personneId = p.personneId
                        Group by FilmId)
                natural left join
                    (select FilmId, listagg(p.Prenom||' '||p.Nom, ',') within group (Order By p.nom) ListActeurs from Film
                        natural join Personnage perso
                        join Personne p on perso.personneId = p.personneId
                        Group by FilmId)
                left join Personne real on real.personneId = realisateurId;
BEGIN
    <<FILM_LOOP>>
    FOR film IN films LOOP
        subStrArray := apex_util.string_to_table(searchString, ' ');
        FOR i in 1..subStrArray.count LOOP
            IsValid:= FALSE;
            term:= subStrArray(i);
            IF REGEXP_LIKE(term, '\(\d{4}\)') THEN
                IF film.anneeSortie = TO_NUMBER(regexp_substr(term, '\d{4}')) THEN
                    IsValid:= TRUE;
                END IF;
            ELSIF REGEXP_LIKE(term, '\[\d{4},\d{4}\]') THEN
                y1:= regexp_substr(term, '\d{4}', 1, 1);
                y2:= regexp_substr(term, '\d{4}', 1, 2);

                IF film.anneeSortie BETWEEN y1 AND y2 THEN
                    IsValid:= TRUE;
                END IF;
            ELSE
                IF UPPER(film.Titre||film.Realisateur||film.ListActeurs||film.ListScenaristes||film.ListGenres||film.ListPays||film.langueOrigine)
                     LIKE '%'||UPPER(term)||'%' THEN
                    IsValid:= TRUE;
                END IF;
            END IF;

            IF NOT IsValid THEN
                CONTINUE FILM_LOOP;
            END IF;

        END LOOP;

        DBMS_OUTPUT.put_line(film.FilmId||'|'||film.Titre);
    END LOOP;
END;

A small disclaimer here :

I saw some similar questions that addressed this issue, but the ones that used cursors were returning a complete select, not hand picked rows.

The question about DBMS_OUTPUT and Hibernate stated that it should be avoided.

The questions using piped rows seamed to work only with functions (Changing the procedure for a function called by the procedure could be a valid work around, I'd like to know if something else is possible before tho).

Body:
The first part of this can probably be accomplished with just a query. You can define your search terms like this: How to declare variable and use it in the same SQL script? (Oracle SQL)

I'll leave the basic query writing to you (e.g. joining appropriate data), but your script will in effect look something like this:

DEFINE var_year1 = 1992;
DEFINE var_year2 = 1994;
DEFINE var_country = null;
DEFINE var_title = 'Lord Of The Rings';
DEFINE var_realisator = null;
DEFINE var_genre = null;
DEFINE var_actors = 'Ian';
DEFINE var_scenarists = 'Lee';

SELECT film_id, title, year
FROM ...
WHERE year BETWEEN &var_year1 AND &var_year2
 AND UPPER(title) LIKE UPPER('%&var_title%')
 AND UPPER(country) LIKE UPPER('%&var_country%')
 AND UPPER(realisator) LIKE UPPER('%&var_realisator%')
 AND UPPER(genre) LIKE UPPER('%&var_genre%')
 AND UPPER(actors) LIKE UPPER('%&var_actors%')
 AND UPPER(scenarists) LIKE UPPER('%&var_scenarists%');
/

The reason I only select film_id, title, and year is because the title and year will be distinct values to the film_id. There are a couple of ways to skin this cat, but it all revolves around using a LIKE statement with variables that you have defined. If you do not want to explicitly define the values in the script, you can use the ACCEPT command. Or, you can interface it with something else that applies those values into the variables.

With this approach, it was kind of a shot in the dark on how you really have your data laid out. But keep in mind good relational database management practices, and you should be able to turn this into a useable query.

Additional Method:

You can also use a series of subqueries to find the same data above using the like statements, then INNER JOIN them together to figure out which ones are in common. Example:

WITH sub_title AS (SELECT film_id FROM Film WHERE UPPER(title) LIKE UPPER('%&var_title%')),
...
sub_actor AS (SELECT film_id FROM (...) WHERE UPPER(actor) LIKE UPPER('%&var_actor%'))
SELECT film_id
FROM sub_title t
     INNER JOIN sub_actor a ON a.film_id = t.film_id;
/

If you had searched for 'star war' in that, you would have returned for example

1   Star Wars A New Hope
2   Star Wars The Empire Strikes Back
3   Star Wars Return of the Jedi

Then in the second subquery if you had searched 'Donald Glover' you would have gotten

2   Star Wars The Empire Strikes Back
3   Star Wars Return of the Jedi

Then, the INNER JOIN would have given you ID numbers 2 and 3 because those were the only ones where all of the criteria were met. Repeat the process for your other search terms. I hope this helps.


问:
Different coloured fly out menu
I'm creating a custom master page for a MOSS publishing site. The designers have come up with this idea for the fly out menu...

alt text http://www.abbeylegal.com/Downloads/2009-01-06/gradient%20menu.jpg

which uses graduated/different backgrond and text colours for each menu option.

Does anyone know how to accomplish this?

答:
I see two possibilites with pure css:

1.
If you have fixed pixel height for the entry lines you could always use one single background image with the gradients on it. If you make your menus with lists you could just slap it on the encompassing list tag.

2.
If you want to to keep the line height/ font size flexible you can work with multiple classes: one for every color tone. Just give give every nth-line a special class with the corresponding color tone as a background color and slap that class on the tag for that line.

design critic:
The problem that I see here is that you will have a maximum number of entries because with this level of gradual fade the background color will become white after six or seven entries.

kind words:
As long as the menu doesn't have to be transparent you should be fine.

OwnerDisplayName: Rob

ContentLicense: CC BY-SA 2.5

Title: Different coloured fly out menu


问:
CORS error with jquery
I'm currently working on a project using the cloudapp API and I'm using jquery.
Here is my code:

```<code> $.ajax({
            headers: { "Accept": "application/json"},
            type: 'GET',
            url: 'http://cl.ly/2wr4',
            crossDomain: true,
            success: function(data, textStatus, request){
                console.log(data);
            }
 });
</code>```

When I run this I get 200 OK response and this error in Firefox:

```<code>Cross-Origin Request Blocked: The Same Origin Policy disallows reading the remote resource at http://cl.ly/2wr4. This can be fixed by moving the resource to the same domain or enabling CORS.
</code>```

and this error in Google Chrome:

```<code>XMLHttpRequest cannot load http://cl.ly/2wr4. No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'null' is therefore not allowed access.
</code>```

and nothing is logged to the console.
Please how can I fix this error?

Thanks.

答:
An important note for those newer coders is that everything on http://enable-cors.org/server.html assumes you have a server running. If you're new, like I was originally, these type of answers don't help.

If you've just made some code on your computer, CodePen, etc - you can't configure this.

There's an important difference between server-side and client-side scripting - your jquery is running on the client side (that is, the users computer / browser) and as such there's no such thing as setting the headers there.

I finally started making progress with this issue when I set up my own server and my own PHP files (PHP is server-side, as such its processed on the server - not the browser) and was able to start making requests just fine.

Adding this for anyone who is being drowned in answers involving the "Header set Access-Control-Allow-Origin "*" answer. It really frustrated me when I started as well.

Title: CORS error with jquery

Body:
I'm currently working on a project using the cloudapp API and I'm using jquery.
Here is my code:

 $.ajax({
            headers: { "Accept": "application/json"},
            type: 'GET',
            url: 'http://cl.ly/2wr4',
            crossDomain: true,
            success: function(data, textStatus, request){
                console.log(data);
            }
 });

When I run this I get 200 OK response and this error in Firefox:

Cross-Origin Request Blocked: The Same Origin Policy disallows reading the remote resource at http://cl.ly/2wr4. This can be fixed by moving the resource to the same domain or enabling CORS.

and this error in Google Chrome:

XMLHttpRequest cannot load http://cl.ly/2wr4. No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'null' is therefore not allowed access.

and nothing is logged to the console.
Please how can I fix this error?

Thanks.


问:
Access files on linux from nodejs with case insensitivity
I am accessing files from nodejs dynamically, but I am facing a problem when user creates a directory with different case like (/hello) and try to access it with different case like (/Hello). Is there a way that I can access directories on linux through nodejs with case insensitivity?</p>

答:
On a case-insensitive filesystem your best bet is probably going to be just reading the list of files in the requested file's directory and do a case-insensitive comparison. For example:</p>

```<code>var requestedPath = '...';
fs.readdir(path.dirname(requestedPath), (err, names) => {
  if (err) throw err;

  var requestedFile = path.basename(requestedPath).toLowerCase();

  for (var i = 0; i < names.length; ++i) {
    if (names[i].toLowerCase() === requestedFilename)
      // do something
  }
});
</code>```

Body:
On a case-insensitive filesystem your best bet is probably going to be just reading the list of files in the requested file's directory and do a case-insensitive comparison. For example:

var requestedPath = '...';
fs.readdir(path.dirname(requestedPath), (err, names) => {
  if (err) throw err;

  var requestedFile = path.basename(requestedPath).toLowerCase();

  for (var i = 0; i < names.length; ++i) {
    if (names[i].toLowerCase() === requestedFilename)
      // do something
  }
});


问:
node not running , websocket error
I'm getting an error when I try to run my node.I have installed ws and websocket, but seems that none is working

答: Simply replace 'const' by 'var'. Strict mode forces you to declare your variables explicitely.</p>

Title: node not running , websocket error


问:
Amazon API Gateway authorization AWS_IAM
What does it means AWS_IAM as Authorization model in Amazon API Gateway?

If I test the Lambda inside the AWS console it works and prints "Hello World", but if I use the endpoint URL and open it inside another browser's tab it say {"message":"Missing Authentication Token"} how can I get this authentication token?

答:
Repeating my answer from our forums:

AWS_IAM authentication means you must sign requests using AWS signature version for and AWS credentials. More details on Signature Version 4 here.

You may want to look at a tool like Postman to generate signatures for testing.

ContentLicense: CC BY-SA 4.0


问:
Slicing pandas dtype object from end not working
I have a dataframe:

where series_id is a dtype object. When I run:

```<code>df['dataType'] = df['series_id'].apply(lambda x: x[-1:])
</code>```

Nothing happens, but when I run:

```<code> df['dataType'] = df['series_id'].apply(lambda x: x[19:20])
</code>```

It creates the correct dataType column.

Any ideas why I can't slice from the end of the object, but from the beginning it works?

答:
and of course the answer was extra whitespace at the end,:

```<code> df['dataType'] = df['series_id'].apply(lambda x: x.strip()[-1:])
</code>```

.strip() takes care of it. Hope that helps someone.

Body:
I have a dataframe:

where series_id is a dtype object. When I run:

df['dataType'] = df['series_id'].apply(lambda x: x[-1:])

Nothing happens, but when I run:

 df['dataType'] = df['series_id'].apply(lambda x: x[19:20])

It creates the correct dataType column.

Any ideas why I can't slice from the end of the object, but from the beginning it works?

Body:
and of course the answer was extra whitespace at the end,:

 df['dataType'] = df['series_id'].apply(lambda x: x.strip()[-1:])

.strip() takes care of it. Hope that helps someone.


问:
help, stored procedures and cursors
i have to write a stored procedure, where you give the month, and a credit card number, and it calulates 1%  for each transaction made in the first 10 days of the month, 2% for transactions between 10 and 20, and 3% for transactions above 20.
And i must use cursors.

i wrote this code, but i get some errors when i try to run the precedure

```<code>   create procedure cardP
   /* month ex 1,3,5 etc*/
   @minas int,
   @cardNo bigint

as
/* creating the cursor*/
DECLARE sinallages CURSOR
FOR SELECT cc_number,day([DateTime]),charged_amount FROM transactions
where cc_number=@cardNo and month([DateTime])=@minas

/* declaring local variables*/
declare @poso int,@karta bigint,@mera int,@pos float,@pos2 float,@pos3 float,
@count int,@counter int

open sinallages

set @count=(select count(cc_number) from transactions where cc_number=@cardNo and month([DateTime])=@minas )
/* get 1st row*/
fetch sinallages into @karta,@mera,@poso
while (/*@@sqlstatus != 2*/@counter<@count)
  begin
    if day(@mera)<=10
    set @pos =@poso+ @poso * 0.01
    else
    if day(@mera)>10 and day(@mera)<=20
    set @pos2 =@poso+ @poso * 0.02
    else
    if day(@mera) > 20
    set @pos3 =@poso+ @poso * 0.03
    fetch sinallages into @karta,@mera,@poso
  set @counter=@counter+1
  end

close sinallages

return
</code>```

when i call the procedure i get

EXEC cardP @minas = 5, @cardNo =4929569752542450

```<code>Msg 16915, Level 16, State 1, Procedure cardP, Line 20
A cursor with the name 'sinallages' already exists.
Msg 16922, Level 16, State 1, Procedure cardP, Line 31
</code>```

Cursor Fetch: Implicit conversion from data type datetime to int is not allowed.

thank you :) i now deallocate the cursor at the end of the stored procedure and removed the day(). Now i want to print the pos+pos2+pos3. I use print  pos+pos2+pos3  but it doesnt print anything. why is that ??

```<code>    ................
      set @counter=@counter+1
  end
print @pos+@pos2+@pos3
close sinallages

return
DEALLOCATE sinallages;
</code>```

it seems like hte variables po,pos2,pos3 are left null??

答:
Others have suggested using DEALLOCATE. The problem with that is that, in some error situations, it won't be called. If you then attempt to use the same connection to call this stored proc, the cursor will still be allocated.

I'd prefer to instead declare the cursor as LOCAL, which means it's automatically deallocated when the stored proc is exited (whether normally or not).

Title: help, stored procedures and cursors

Body:
i have to write a stored procedure, where you give the month, and a credit card number, and it calulates 1%  for each transaction made in the first 10 days of the month, 2% for transactions between 10 and 20, and 3% for transactions above 20.
And i must use cursors.

i wrote this code, but i get some errors when i try to run the precedure

   create procedure cardP
   /* month ex 1,3,5 etc*/
   @minas int,
   @cardNo bigint

as
/* creating the cursor*/
DECLARE sinallages CURSOR
FOR SELECT cc_number,day([DateTime]),charged_amount FROM transactions
where cc_number=@cardNo and month([DateTime])=@minas

/* declaring local variables*/
declare @poso int,@karta bigint,@mera int,@pos float,@pos2 float,@pos3 float,
@count int,@counter int

open sinallages

set @count=(select count(cc_number) from transactions where cc_number=@cardNo and month([DateTime])=@minas )
/* get 1st row*/
fetch sinallages into @karta,@mera,@poso
while (/*@@sqlstatus != 2*/@counter<@count)
  begin
    if day(@mera)<=10
    set @pos =@poso+ @poso * 0.01
    else
    if day(@mera)>10 and day(@mera)<=20
    set @pos2 =@poso+ @poso * 0.02
    else
    if day(@mera) > 20
    set @pos3 =@poso+ @poso * 0.03
    fetch sinallages into @karta,@mera,@poso
  set @counter=@counter+1
  end

close sinallages

return

when i call the procedure i get

EXEC cardP @minas = 5, @cardNo =4929569752542450

Msg 16915, Level 16, State 1, Procedure cardP, Line 20
A cursor with the name 'sinallages' already exists.
Msg 16922, Level 16, State 1, Procedure cardP, Line 31

Cursor Fetch: Implicit conversion from data type datetime to int is not allowed.

thank you :) i now deallocate the cursor at the end of the stored procedure and removed the day(). Now i want to print the pos+pos2+pos3. I use print  pos+pos2+pos3  but it doesnt print anything. why is that ??

    ................
      set @counter=@counter+1
  end
print @pos+@pos2+@pos3
close sinallages

return
DEALLOCATE sinallages;

it seems like hte variables po,pos2,pos3 are left null??


问:
Trying to use filter function on strings
i have the following function and I am trying to make a list containing the 'tweet numbers' of tweets done by DanClark . I am splitting the strings and trying to use the filter function to produce it. I am trying to avoid explicit recursion. i keep getting the following error " 'str' object is not callable" when i try to run "search_tweets(tweets, "DanClark")"</p>

```<code>tweet1 = "#1::@DanClark::The party was amazing"
tweet19 = "#19::@NatalyS::Avoid 401 Toronto area at this time"
tweet50 = "#50::@CBCNews::How Canadian captain gave her team a speech"
tweet14 = "#14::@DanClark::The food was good"
tweet15 = "#15::@DaveLin::Lucky you DanClark"
tweets =   [tweet1, tweet19, tweet50, tweet14, tweet15]

def separator(tweets, item1, item2, tweeter):

part1 = (tweets[item1].split('::'))
part2 = part1[item2]
part3 = part2[1:]

  if part3 == tweeter:
      return (part1[0])[1:]
  else:
      return []

def search_tweets(tweets, tweeter):
  return list(filter((separator(tweets, 0, 1, tweeter)), tweets))
</code>```

答:
I believe filter expects the first argument to be a function whereas you are giving it the return value of your call to separator.

From python docs:

Note that filter(function, iterable) is equivalent to the generator expression (item for item in iterable if function(item))

Body:
i have the following function and I am trying to make a list containing the 'tweet numbers' of tweets done by DanClark . I am splitting the strings and trying to use the filter function to produce it. I am trying to avoid explicit recursion. i keep getting the following error " 'str' object is not callable" when i try to run "search_tweets(tweets, "DanClark")"

tweet1 = "#1::@DanClark::The party was amazing"
tweet19 = "#19::@NatalyS::Avoid 401 Toronto area at this time"
tweet50 = "#50::@CBCNews::How Canadian captain gave her team a speech"
tweet14 = "#14::@DanClark::The food was good"
tweet15 = "#15::@DaveLin::Lucky you DanClark"
tweets =   [tweet1, tweet19, tweet50, tweet14, tweet15]

def separator(tweets, item1, item2, tweeter):

part1 = (tweets[item1].split('::'))
part2 = part1[item2]
part3 = part2[1:]

  if part3 == tweeter:
      return (part1[0])[1:]
  else:
      return []

def search_tweets(tweets, tweeter):
  return list(filter((separator(tweets, 0, 1, tweeter)), tweets))