问:
Order of object in 3d plot - spiral
I plotted a spiral and a line that should go through the spiral. I am not able to set that the line is behind the front part of the spiral and in front of the back part of the spiral. I tried to use zorder but the line is either whole in front of the spiral or whole behind the spiral. Thank you

Code:

```<code>import matplotlib as mpl
from mpl_toolkits.mplot3d import Axes3D
import numpy as np
import matplotlib.pyplot as plt

mpl.rcParams['legend.fontsize'] = 10

fig = plt.figure()
ax = fig.gca(projection='3d')
theta = np.linspace(-4 * np.pi, 4 * np.pi, 100)
z = np.linspace(-2, 2, 100)
r = z**2 + 1
x = r * np.sin(theta)
y = r * np.cos(theta)
ax.plot(x, y, z, label='parametric curve')

ax.plot([-1,-1], # x
        [2,2], # y
        [-2, 2], c='red')

plt.show()
</code>```

For instance, here. The red line is in front of the spiral. If I set zorder it could be behind the spiral. How to set the line goes properly throught the spiral?

答:
Note that matplotlib isn't fully 3D. In order to get enough speed for complex plots, 3D is simulated drawing everything back to front, with each element drawn in its entirety on a specific depth. If you need full 3D, packages such as mayavi are worth investigating.

In order to get the red line inside the spiral, using matplotlib, the following approach can be used:

draw the spiral

draw the red line

draw the spiral again, but only the part that would be in front of the line

Note that such an approach only works if you don't rotate the view too much and you don't use transparency.

Now, to draw only a part of a curve, the standard way uses numpy's masked arrays. But these don't seem to be respected by the 3D plot. The alternative is to set unwanted points to NaN.

To better demonstrates the approach, the code below draws the red line much wider and uses green for the part of the spiral in front of the line. For the real thing, the spiral and the partial spiral would use the same colors.

from mpl_toolkits.mplot3d import Axes3D
import numpy as np
import matplotlib.pyplot as plt

fig = plt.figure()
ax = fig.gca(projection='3d')
theta = np.linspace(-4 * np.pi, 4 * np.pi, 100)
z = np.linspace(-2, 2, 100)
r = z**2 + 1
x = r * np.sin(theta)
y = r * np.cos(theta)
ax.plot(x, y, z, label='parametric curve') # the full spiral

ax.plot([-1,-1], # x
        [2,2], # y
        [-2, 2], c='red', lw=10)

ym = np.copy(y)
ym[y > 0] = np.NaN
ax.plot(x, ym, z, color='lime') # partial spiral

plt.show()
```

Title: Order of object in 3d plot - spiral

Body:
I plotted a spiral and a line that should go through the spiral. I am not able to set that the line is behind the front part of the spiral and in front of the back part of the spiral. I tried to use zorder but the line is either whole in front of the spiral or whole behind the spiral. Thank you

Code:

import matplotlib as mpl
from mpl_toolkits.mplot3d import Axes3D
import numpy as np
import matplotlib.pyplot as plt

mpl.rcParams['legend.fontsize'] = 10

fig = plt.figure()
ax = fig.gca(projection='3d')
theta = np.linspace(-4 * np.pi, 4 * np.pi, 100)
z = np.linspace(-2, 2, 100)
r = z**2 + 1
x = r * np.sin(theta)
y = r * np.cos(theta)
ax.plot(x, y, z, label='parametric curve')

ax.plot([-1,-1], # x
        [2,2], # y
        [-2, 2], c='red')

plt.show()

For instance, here. The red line is in front of the spiral. If I set zorder it could be behind the spiral. How to set the line goes properly throught the spiral?


来源: stackexchange

问:
How can you create a user and a company model at the same time? Laravel
I have a simple register account form on my front page, and I want that when a user is created, a company model is created in the same instence with a user model, but I don't know how to properly define it.

```<code>public function create(Request $request) {

    $create = User::create([
        'email' => $request['email'],
        'paypal_email' => $request['paypal_email'],
        'password' => Hash::make($request['password']),
    ]);
    if($create){

        return redirect('/dashboard');
    }
}
}
</code>```

User model:

```<code>class User extends Authenticatable
{
use Notifiable;

/**
 * The attributes that are mass assignable.
 *
 * @var array
 */
protected $fillable = [
     'email', 'password', 'paypal_email', 'first_name', 'last_name',
'email_verified_at', 'user_id'
];

/**
 * The attributes that should be hidden for arrays.
 *
 * @var array
 */
protected $hidden = [
    'password', 'remember_token',
];

/**
 * The attributes that should be cast to native types.
 *
 * @var array
 */
protected $casts = [
    'email_verified_at' => 'datetime',
];

/**
 * Get user company
 * @return \Illuminate\Database\Eloquent\Relations\HasOne
 */

public function company ()
{
    return $this->hasOne(Company::class);
}
}
</code>```

Company model:

```<code>class Company extends Authenticatable
{
 use Notifiable;

/**
 * The attributes that are mass assignable.
 *
 * @var array
 */
protected $fillable = [
    'company_name', 'phone', 'gst_hst_number', 'country'
];

/**
 * The attributes that should be hidden for arrays.
 *
 * @var array
 */
protected $hidden = [

];

public function user()
{
    return $this->belongsTo(User::class);
}
}
</code>```

create_companies_table values are all nullable, the logic is, that you can update all info later, but when you create a user, a company model is created also, the data in the tables you can fill later.

How can I properly define the create function?

答:
You can check if the User is created successfully.

```<code>if ($create) {
    // This will create your company by passing empty attribute to it, since all of the fields in the model are nullable.
    Company::create(['user_id' => $create->id]);
}
</code>```

If I was you I would do this in the model. I would make a method that will do that for me. Lets say that I will create a createWithCompany method in the User model and do something like this:

```<code>public static function createWithCompany($attributes)
{

// Begin a transaction since we are creating a company and then the user.
    DB::beginTransaction();

    Try {
// We create the company
        $comapny = Copmany::create([]);

// Creates the user with the needed data.
        $user = self::create(array_merge($attributes, ['company_id' => $company->id]));
// We commit everything if we have no errors during the insert
        DB::commit();
    } catch (\Exception $e) {
// We rollback the company and the user if one of them fails to be created.
        DB::rollBack();
    }

    return $user;
}
</code>```

The benefit of this approach is that if later on you want to create from the console with a command some kind of script that inserts Users and creates companies for them you can do this with a single method and the code with be consistent with your controller.

I'm assuming that 1 company can have many users.

ContentLicense: CC BY-SA 4.0

Body:
I have a simple register account form on my front page, and I want that when a user is created, a company model is created in the same instence with a user model, but I don't know how to properly define it.

public function create(Request $request) {

    $create = User::create([
        'email' => $request['email'],
        'paypal_email' => $request['paypal_email'],
        'password' => Hash::make($request['password']),
    ]);
    if($create){

        return redirect('/dashboard');
    }
}
}

User model:

class User extends Authenticatable
{
use Notifiable;

/**
 * The attributes that are mass assignable.
 *
 * @var array
 */
protected $fillable = [
     'email', 'password', 'paypal_email', 'first_name', 'last_name',
'email_verified_at', 'user_id'
];

/**
 * The attributes that should be hidden for arrays.
 *
 * @var array
 */
protected $hidden = [
    'password', 'remember_token',
];

/**
 * The attributes that should be cast to native types.
 *
 * @var array
 */
protected $casts = [
    'email_verified_at' => 'datetime',
];

/**
 * Get user company
 * @return \Illuminate\Database\Eloquent\Relations\HasOne
 */

public function company ()
{
    return $this->hasOne(Company::class);
}
}

Company model:

class Company extends Authenticatable
{
 use Notifiable;

/**
 * The attributes that are mass assignable.
 *
 * @var array
 */
protected $fillable = [
    'company_name', 'phone', 'gst_hst_number', 'country'
];

/**
 * The attributes that should be hidden for arrays.
 *
 * @var array
 */
protected $hidden = [

];

public function user()
{
    return $this->belongsTo(User::class);
}
}

create_companies_table values are all nullable, the logic is, that you can update all info later, but when you create a user, a company model is created also, the data in the tables you can fill later.

How can I properly define the create function?

Body:
You can check if the User is created successfully.

if ($create) {
    // This will create your company by passing empty attribute to it, since all of the fields in the model are nullable.
    Company::create(['user_id' => $create->id]);
}

If I was you I would do this in the model. I would make a method that will do that for me. Lets say that I will create a createWithCompany method in the User model and do something like this:

public static function createWithCompany($attributes)
{

// Begin a transaction since we are creating a company and then the user.
    DB::beginTransaction();

    Try {
// We create the company
        $comapny = Copmany::create([]);

// Creates the user with the needed data.
        $user = self::create(array_merge($attributes, ['company_id' => $company->id]));
// We commit everything if we have no errors during the insert
        DB::commit();
    } catch (\Exception $e) {
// We rollback the company and the user if one of them fails to be created.
        DB::rollBack();
    }

    return $user;
}

The benefit of this approach is that if later on you want to create from the console with a command some kind of script that inserts Users and creates companies for them you can do this with a single method and the code with be consistent with your controller.

I'm assuming that 1 company can have many users.


问:
How can I pass a value with a $ to a program run through su?
I need to run one of the script as below:

su - oracle -c 'cd /tmp/somepath; sh -x myscript.sh arg1 arg2 arg3
  obj$_jghd$:jhdbcdj:hshabsh'

where arg4(obj$_jghd$:jhdbcdj:hshabsh) should be treated as one argument and calling in for loop in myscript.sh
Below is the sample code

```<code>id1=$1
id2=$2
id3=$3
name=$4
S_Object=`echo ""${name}""|sed 's/:/ /g'`
</code>```

here I am reformating agr4 and removing the delimiter : with space and trying to nullify $. But when running the script all variables are not getting stored which contains $ and getting this error:

```<code>+ name='obj$:jhdbcdj:hshabsh'
++ echo 'obj$:jhdbcdj:hshabsh'
++ sed 's/:/ /g'
++ sed '/s/$/$/g'
sed: -e expression #1, char 4: unknown command: `$'
</code>```

Can you please help to get the right string stored in name variable.

I want the result should be like :

```<code>echo $S_Object

S_Object='obj$_jghd$ jhdbcdj hshabsh'
</code>```

but I am getting as below :

```<code>echo $S_Object
S_Object='obj$ jhdbcdj hshabsh'
</code>```

答:
Change the second sed command to sed 's/$ /$_/g'
then you should get your desired output.

Body:
I need to run one of the script as below:

su - oracle -c 'cd /tmp/somepath; sh -x myscript.sh arg1 arg2 arg3
  obj$_jghd$:jhdbcdj:hshabsh'

where arg4(obj$_jghd$:jhdbcdj:hshabsh) should be treated as one argument and calling in for loop in myscript.sh
Below is the sample code

id1=$1
id2=$2
id3=$3
name=$4
S_Object=`echo ""${name}""|sed 's/:/ /g'`

here I am reformating agr4 and removing the delimiter : with space and trying to nullify $. But when running the script all variables are not getting stored which contains $ and getting this error:

+ name='obj$:jhdbcdj:hshabsh'
++ echo 'obj$:jhdbcdj:hshabsh'
++ sed 's/:/ /g'
++ sed '/s/$/$/g'
sed: -e expression #1, char 4: unknown command: `$'

Can you please help to get the right string stored in name variable.

I want the result should be like :

echo $S_Object

S_Object='obj$_jghd$ jhdbcdj hshabsh'

but I am getting as below :

echo $S_Object
S_Object='obj$ jhdbcdj hshabsh'


问:
how to display a data table with blank rows using jsf 2.0
I'm trying to show a empty datatable with 10 rows on the page load, when i try using the below code, it does not show any rows.

```<code><h:dataTable id="d" value="" bgcolor="#9AC8E6" border="10" cellpadding="5" cellspacing="3" rows="10" width="100%" dir="LTR" frame="hsides" rules="all" >
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Student Number" />
                        </f:facet>
                        <h:inputText value="#{10}" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Student Name" />
                        </f:facet>
                        <h:inputText value="" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Standard" />
                        </f:facet>
                        <h:inputText value="" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Marks" />
                        </f:facet>
                        <h:inputText value="" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Percentage" />
                        </f:facet>
                        <h:inputText value="" > </h:inputText>
                    </h:column>
                    <h:column>
                </h:dataTable>
</code>```

Need help to display a datatable with blank columns and rows

UPDATE

According to the given solution I tried this way but could not resolve the problem

```<code>   <h:dataTable id="d" value="#{inquiryBean.blankList}" var="emptyBean" bgcolor="#9AC8E6" border="10" cellpadding="5" cellspacing="3" rows="10" width="100%" dir="LTR" frame="hsides" rules="all" >
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Item Number" />
                        </f:facet>
                        <h:inputText value="#{emptyBean.itemNumber}" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Material" />
                        </f:facet>
                        <h:inputText value="#{emptyBean.material}" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Description" />
                        </f:facet>
                        <h:inputText value="#{emptyBean.description}" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Unit" />
                        </f:facet>
                        <h:inputText value="#{emptyBean.unit}" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Quantity" />
                        </f:facet>
                        <h:inputText value="#{emptyBean.quantity}" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Delivery Date" />
                        </f:facet>
                        <h:inputText value="#{emptyBean.deliveryDate}" > </h:inputText>
                    </h:column>
                </h:dataTable>
</code>```

## Bean Class ##

```<code>//getters and setters
List blankList = new ArrayList();

public List getBlankList() {
    InquiryBean bean = new InquiryBean();
    bean.setItemNumber("");
    bean.setMaterial("");
    bean.setDescription("");
    bean.setQuantity("");
    bean.setUnit("");
    bean.setDeliveryDate(null);
    return blankList;
}
</code>```

Am i missing something????

答:
If you do not want to fill it later you could use a plain html table instead:

```<code><table>
  <tr>
    <td>Student Number</td><td>Student Name</td> ...
  </tr>
  <tr>
    <td></td><td></td> ...
  </tr>
  <!-- 9 rows following -->
</table>
</code>```

If you want to fill it later you have to use the var attribute of the dataTable and prepare a list with 10 (empty) elements in the backing bean:

```<code><h:dataTable value=#{myBean.studentList} var="item">
  <h:column>
    <f:facet name="header">
       <h:outputText value="Student Number" />
    </f:facet>
     <h:inputText value="#{item.studNum}" />
  </h:column>
  ..
</h:dataTable>
</code>```

ContentLicense: CC BY-SA 3.0

Body:
I'm trying to show a empty datatable with 10 rows on the page load, when i try using the below code, it does not show any rows.

<h:dataTable id="d" value="" bgcolor="#9AC8E6" border="10" cellpadding="5" cellspacing="3" rows="10" width="100%" dir="LTR" frame="hsides" rules="all" >
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Student Number" />
                        </f:facet>
                        <h:inputText value="#{10}" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Student Name" />
                        </f:facet>
                        <h:inputText value="" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Standard" />
                        </f:facet>
                        <h:inputText value="" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Marks" />
                        </f:facet>
                        <h:inputText value="" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Percentage" />
                        </f:facet>
                        <h:inputText value="" > </h:inputText>
                    </h:column>
                    <h:column>
                </h:dataTable>

Need help to display a datatable with blank columns and rows

UPDATE

According to the given solution I tried this way but could not resolve the problem

   <h:dataTable id="d" value="#{inquiryBean.blankList}" var="emptyBean" bgcolor="#9AC8E6" border="10" cellpadding="5" cellspacing="3" rows="10" width="100%" dir="LTR" frame="hsides" rules="all" >
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Item Number" />
                        </f:facet>
                        <h:inputText value="#{emptyBean.itemNumber}" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Material" />
                        </f:facet>
                        <h:inputText value="#{emptyBean.material}" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Description" />
                        </f:facet>
                        <h:inputText value="#{emptyBean.description}" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Unit" />
                        </f:facet>
                        <h:inputText value="#{emptyBean.unit}" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Quantity" />
                        </f:facet>
                        <h:inputText value="#{emptyBean.quantity}" > </h:inputText>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText style=""value="Delivery Date" />
                        </f:facet>
                        <h:inputText value="#{emptyBean.deliveryDate}" > </h:inputText>
                    </h:column>
                </h:dataTable>

## Bean Class ##

//getters and setters
List blankList = new ArrayList();

public List getBlankList() {
    InquiryBean bean = new InquiryBean();
    bean.setItemNumber("");
    bean.setMaterial("");
    bean.setDescription("");
    bean.setQuantity("");
    bean.setUnit("");
    bean.setDeliveryDate(null);
    return blankList;
}

Am i missing something????

Body:
If you do not want to fill it later you could use a plain html table instead:

<table>
  <tr>
    <td>Student Number</td><td>Student Name</td> ...
  </tr>
  <tr>
    <td></td><td></td> ...
  </tr>
  <!-- 9 rows following -->
</table>

If you want to fill it later you have to use the var attribute of the dataTable and prepare a list with 10 (empty) elements in the backing bean:

<h:dataTable value=#{myBean.studentList} var="item">
  <h:column>
    <f:facet name="header">
       <h:outputText value="Student Number" />
    </f:facet>
     <h:inputText value="#{item.studNum}" />
  </h:column>
  ..
</h:dataTable>


问:
Print the next line after the pattern match using perl
There is a similar question is there before, But mine is little bit different question. so am modifying a bit and posting here for help.

```<code> Car Type, Price,  Colour,

 N17,       200$    white
 A57,       250$    Red
 L45,       350$    Black
</code>```

Below is the code am having currently.

```<code>my @cartype;
while (@cartype = <FH1> ) {

    my $i = 0;

    foreach my $a (@cartype) {
        if ($a =~ m/(Car)/ )  {
            my $b = $cartype[$i+1];
            push (@cartype, $b);
            print $b;
        }

        $i++;
    }
}

close;
</code>```

Current Output:

```<code> N17,       200$    white
 A57,       250$    Red
 L45,       350$    Black
</code>```

I would like to print next line after the pattern match but it is printing the whole next line, instead of that i just need only that particular column, like if am searching for a pattern called "car" only car types should display instead of whole next line.

Expected Output:

```<code>    Car Type
       N17
       A57
       L45
       ..
       .
</code>```

答:
Why not to try something in following spirit?</p>

```<code>use strict;
use warnings;
use feature 'say';

use Data::Dumper;

my $debug = 0;      # debug flag

my $look_for = shift || usage();

my %cars;

my @header = map{ s/(^ +| +$)//; $_ } (split ',', <DATA> );

chomp @header;      # clean up header fields

say Dumper(\@header) if $debug;

while(<DATA>) {
    next if /^ *$/;                             # skip empty lines
    chomp;                                      # snip eol
    if( /(\w\d{2}), +(\d{3}\$) +(\w+)/ ) {      # our data
        @{$cars{$1}}{@header} = ($1,$2,$3);     # fill %cars with data
    }
}

say Dumper(\%cars) if $debug;

$look_for = 'Car Type' if $look_for eq 'Car';
$look_for = 'Car Type' if $look_for eq 'Type';

say "\nLooking for: $look_for\n";

while( my($k,$v) = each %cars ) {
    say "  " . $v->{$look_for};                 # print field of interest
}

sub usage {
    say
"
    USAGE: $0 [Car|Type|Colour|Price]
";
    exit 0;
}

__DATA__
Car Type, Price,  Colour

N17,       200$    white
A57,       250$    Red
L45,       350$    Black
</code>```

Body:
There is a similar question is there before, But mine is little bit different question. so am modifying a bit and posting here for help.

 Car Type, Price,  Colour,

 N17,       200$    white
 A57,       250$    Red
 L45,       350$    Black

Below is the code am having currently.

my @cartype;
while (@cartype = <FH1> ) {

    my $i = 0;

    foreach my $a (@cartype) {
        if ($a =~ m/(Car)/ )  {
            my $b = $cartype[$i+1];
            push (@cartype, $b);
            print $b;
        }

        $i++;
    }
}

close;

Current Output:

 N17,       200$    white
 A57,       250$    Red
 L45,       350$    Black

I would like to print next line after the pattern match but it is printing the whole next line, instead of that i just need only that particular column, like if am searching for a pattern called "car" only car types should display instead of whole next line.

Expected Output:

    Car Type
       N17
       A57
       L45
       ..
       .

Body:
Why not to try something in following spirit?

use strict;
use warnings;
use feature 'say';

use Data::Dumper;

my $debug = 0;      # debug flag

my $look_for = shift || usage();

my %cars;

my @header = map{ s/(^ +| +$)//; $_ } (split ',', <DATA> );

chomp @header;      # clean up header fields

say Dumper(\@header) if $debug;

while(<DATA>) {
    next if /^ *$/;                             # skip empty lines
    chomp;                                      # snip eol
    if( /(\w\d{2}), +(\d{3}\$) +(\w+)/ ) {      # our data
        @{$cars{$1}}{@header} = ($1,$2,$3);     # fill %cars with data
    }
}

say Dumper(\%cars) if $debug;

$look_for = 'Car Type' if $look_for eq 'Car';
$look_for = 'Car Type' if $look_for eq 'Type';

say "\nLooking for: $look_for\n";

while( my($k,$v) = each %cars ) {
    say "  " . $v->{$look_for};                 # print field of interest
}

sub usage {
    say
"
    USAGE: $0 [Car|Type|Colour|Price]
";
    exit 0;
}

__DATA__
Car Type, Price,  Colour

N17,       200$    white
A57,       250$    Red
L45,       350$    Black


问:
Vue.js: To Get Environment Variables in js File
I have created .env file to set environment variables as shown below:

Inside which I have given below mentioned code.

```<code>VUE_APP_BASEURL="https://qa-apps-nodejs.Dtech.com:9000/"
PORT=8080
</code>```

I have written below code in my js file and executed npm install dotenv:

```<code>require('dotenv').config();
console.log(process.env.VUE_APP_BASEURL);
</code>```

With the above code, I need to get https://qa-apps-nodejs.Dtech.com:9000/ in console. But instead I'm getting:

undefined

答: Just restart your server as newly created env variables are not available only after hot-reload you have to rebuild your application (restart your server). For reference you can look here</p>

Body:
I have created .env file to set environment variables as shown below:

Inside which I have given below mentioned code.

VUE_APP_BASEURL="https://qa-apps-nodejs.Dtech.com:9000/"
PORT=8080

I have written below code in my js file and executed npm install dotenv:

require('dotenv').config();
console.log(process.env.VUE_APP_BASEURL);

With the above code, I need to get https://qa-apps-nodejs.Dtech.com:9000/ in console. But instead I'm getting:

undefined


问:
i am getting this type of error while running the program of recycle view in android
```<code>  E/AndroidRuntime: FATAL EXCEPTION: main
     Process: com.example.spammessagedetector, PID: 2137
     java.lang.RuntimeException: Unable to start activity ComponentInfo{com.example.spammessagedetector/com.example.spammessagedetector.Inbox}:
 java.lang.NullPointerException: Attempt to invoke virtual method 'void
 androidx.swiperefreshlayout.widget.SwipeRefreshLayout.setOnRefreshListener(androidx.swiperefreshlayout.widget.SwipeRefreshLayout$OnRefreshListener)'
 on a null object reference
         at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2646)
         at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2707)
         at android.app.ActivityThread.-wrap12(ActivityThread.java)
         at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1460)
         at android.os.Handler.dispatchMessage(Handler.java:102)
         at android.os.Looper.loop(Looper.java:154)
         at android.app.ActivityThread.main(ActivityThread.java:6077)
         at java.lang.reflect.Method.invoke(Native Method)
         at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:866)
         at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:756)
      Caused by: java.lang.NullPointerException: Attempt to invoke virtual method 'void
 androidx.swiperefreshlayout.widget.SwipeRefreshLayout.setOnRefreshListener(androidx.swiperefreshlayout.widget.SwipeRefreshLayout$OnRefreshListener)'
 on a null object reference
         at com.example.spammessagedetector.Inbox.onCreate(Inbox.java:76)
         at android.app.Activity.performCreate(Activity.java:6662)
         at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1118)
         at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2599)
         at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2707)
   at android.app.ActivityThread.-wrap12(ActivityThread.java)
         at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1460)
         at android.os.Handler.dispatchMessage(Handler.java:102)
         at android.os.Looper.loop(Looper.java:154)
         at android.app.ActivityThread.main(ActivityThread.java:6077)
         at java.lang.reflect.Method.invoke(Native Method)
         at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:866)
  at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:756)
</code>```

here is the code for    Inbox.java

```<code>package com.example.spammessagedetector;

import androidx.appcompat.app.AppCompatActivity;
import androidx.appcompat.view.ActionMode;
import androidx.appcompat.widget.Toolbar;
import androidx.recyclerview.widget.DefaultItemAnimator;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import androidx.swiperefreshlayout.widget.SwipeRefreshLayout;

import android.os.Bundle;

import android.content.res.TypedArray;
import android.graphics.Color;
import android.os.Bundle;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.widget.Toast;
import java.util.ArrayList;
import java.util.List;

import com.example.spammessagedetector.R;
import com.example.spammessagedetector.adapter.MessagesAdapter;
import com.example.spammessagedetector.helper.DividerItemDecoration;
import com.example.spammessagedetector.model.Message;
import com.example.spammessagedetector.network.ApiClient;
import com.example.spammessagedetector.network.ApiInterface;
import com.google.android.material.floatingactionbutton.FloatingActionButton;
import com.google.android.material.snackbar.Snackbar;

import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;

public class Inbox extends AppCompatActivity implements SwipeRefreshLayout.OnRefreshListener, MessagesAdapter.MessageAdapterListener{

    private List<Message> messages = new ArrayList<>();
    private RecyclerView recyclerView;
    private MessagesAdapter mAdapter;
    private SwipeRefreshLayout swipeRefreshLayout;
    private ActionModeCallback actionModeCallback;
    private ActionMode actionMode;

    @Override
    protected void onCreate(Bundle savedInstanceState) {

        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_inbox);
        setContentView(R.layout.activity_main);
        Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
        setSupportActionBar(toolbar);

        FloatingActionButton fab = (FloatingActionButton) findViewById(R.id.fab);
        if (fab != null)
        fab.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                Snackbar.make(view, "Replace with your own action", Snackbar.LENGTH_LONG)
                        .setAction("Action", null).show();
            }
        });

        recyclerView = (RecyclerView) findViewById(R.id.recycler_view);
        swipeRefreshLayout = (SwipeRefreshLayout) findViewById(R.id.swipe_refresh_layout);
        swipeRefreshLayout.setOnRefreshListener(this);

        mAdapter = new MessagesAdapter(this, messages, this);
        RecyclerView.LayoutManager mLayoutManager = new LinearLayoutManager(getApplicationContext());
        recyclerView.setLayoutManager(mLayoutManager);
        recyclerView.setItemAnimator(new DefaultItemAnimator());
        recyclerView.addItemDecoration(new DividerItemDecoration(this, LinearLayoutManager.VERTICAL));
        recyclerView.setAdapter(mAdapter);

        actionModeCallback = new ActionModeCallback();

        // show loader and fetch messages
        swipeRefreshLayout.post(
                new Runnable() {
                    @Override
                    public void run() {
                        getInbox();
                    }
                }
        );
    }

    /**
     * Fetches mail messages by making HTTP request
     * url: https://api.androidhive.info/json/inbox.json
     */
    private void getInbox() {
        swipeRefreshLayout.setRefreshing(true);

        ApiInterface apiService =
                ApiClient.getClient().create(ApiInterface.class);

        Call<List<Message>> call = apiService.getInbox();
        call.enqueue(new Callback<List<Message>>() {
            @Override
            public void onResponse(Call<List<Message>> call, Response<List<Message>> response) {
                // clear the inbox
                messages.clear();

                // add all the messages
                // messages.addAll(response.body());

                // TODO - avoid looping
                // the loop was performed to add colors to each message
                for (Message message : response.body()) {
                    // generate a random color
                    message.setColor(getRandomMaterialColor("400"));
                    messages.add(message);
                }

                mAdapter.notifyDataSetChanged();
                swipeRefreshLayout.setRefreshing(false);
            }

            @Override
            public void onFailure(Call<List<Message>> call, Throwable t) {
                Toast.makeText(getApplicationContext(), "Unable to fetch json: " + t.getMessage(), Toast.LENGTH_LONG).show();
                swipeRefreshLayout.setRefreshing(false);
            }
        });
    }

    /**
     * chooses a random color from array.xml
     */
    private int getRandomMaterialColor(String typeColor) {
        int returnColor = Color.GRAY;
        int arrayId = getResources().getIdentifier("mdcolor_" + typeColor, "array", getPackageName());

        if (arrayId != 0) {
            TypedArray colors = getResources().obtainTypedArray(arrayId);
            int index = (int) (Math.random() * colors.length());
            returnColor = colors.getColor(index, Color.GRAY);
            colors.recycle();
        }
        return returnColor;
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.menu_main, menu);
        return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        // Handle action bar item clicks here. The action bar will
        // automatically handle clicks on the Home/Up button, so long
        // as you specify a parent activity in AndroidManifest.xml.
        int id = item.getItemId();

        //noinspection SimplifiableIfStatement
        if (id == R.id.action_search) {
            Toast.makeText(getApplicationContext(), "Search...", Toast.LENGTH_SHORT).show();
            return true;
        }

        return super.onOptionsItemSelected(item);
    }

    @Override
    public void onRefresh() {
        // swipe refresh is performed, fetch the messages again
        getInbox();
    }

    @Override
    public void onIconClicked(int position) {
        if (actionMode == null) {
            actionMode = startSupportActionMode(actionModeCallback);
        }

        toggleSelection(position);
    }

    @Override
    public void onIconImportantClicked(int position) {
        // Star icon is clicked,
        // mark the message as important
        Message message = messages.get(position);
        message.setImportant(!message.isImportant());
        messages.set(position, message);
        mAdapter.notifyDataSetChanged();
    }

    @Override
    public void onMessageRowClicked(int position) {
        // verify whether action mode is enabled or not
        // if enabled, change the row state to activated
        if (mAdapter.getSelectedItemCount() > 0) {
            enableActionMode(position);
        } else {
            // read the message which removes bold from the row
            Message message = messages.get(position);
            message.setRead(true);
            messages.set(position, message);
            mAdapter.notifyDataSetChanged();

            Toast.makeText(getApplicationContext(), "Read: " + message.getMessage(), Toast.LENGTH_SHORT).show();
        }
    }

    @Override
    public void onRowLongClicked(int position) {
        // long press is performed, enable action mode
        enableActionMode(position);
    }

    private void enableActionMode(int position) {
        if (actionMode == null) {
            actionMode = startSupportActionMode(actionModeCallback);
        }
        toggleSelection(position);
    }

    private void toggleSelection(int position) {
        mAdapter.toggleSelection(position);
        int count = mAdapter.getSelectedItemCount();

        if (count == 0) {
            actionMode.finish();
        } else {
            actionMode.setTitle(String.valueOf(count));
            actionMode.invalidate();
        }
    }

    private class ActionModeCallback implements ActionMode.Callback {
        @Override
        public boolean onCreateActionMode(ActionMode mode, Menu menu) {
            mode.getMenuInflater().inflate(R.menu.menu_action_mode, menu);

            // disable swipe refresh if action mode is enabled
            swipeRefreshLayout.setEnabled(false);
            return true;
        }

        @Override
        public boolean onPrepareActionMode(ActionMode mode, Menu menu) {
            return false;
        }

        @Override
        public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
            switch (item.getItemId()) {
                case R.id.action_delete:
                    // delete all the selected messages
                    deleteMessages();
                    mode.finish();
                    return true;

                default:
                    return false;
            }
        }

        @Override
        public void onDestroyActionMode(ActionMode mode) {
            mAdapter.clearSelections();
            swipeRefreshLayout.setEnabled(true);
            actionMode = null;
            recyclerView.post(new Runnable() {
                @Override
                public void run() {
                    mAdapter.resetAnimationIndex();
                    // mAdapter.notifyDataSetChanged();
                }
            });
        }
    }

    // deleting the messages from recycler view
    private void deleteMessages() {
        mAdapter.resetAnimationIndex();
        List<Integer> selectedItemPositions =
                mAdapter.getSelectedItems();
        for (int i = selectedItemPositions.size() - 1; i >= 0; i--) {
            mAdapter.removeData(selectedItemPositions.get(i));
        }
        mAdapter.notifyDataSetChanged();
    }
}
</code>```

activity_inbox.xml

```<code>

     <?xml version="1.0" encoding="utf-8"?>
    <androidx.coordinatorlayout.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:app="http://schemas.android.com/apk/res-auto"
        xmlns:tools="http://schemas.android.com/tools"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        tools:mContext=".Inbox">

        <com.google.android.material.appbar.AppBarLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:theme="@style/AppTheme.AppBarOverlay">

            <androidx.appcompat.widget.Toolbar
                android:id="@+id/toolbar"
                android:layout_width="match_parent"
                android:layout_height="?attr/actionBarSize"
                android:background="?attr/colorPrimary"
                app:popupTheme="@style/AppTheme.PopupOverlay"/>
        </com.google.android.material.appbar.AppBarLayout>

        <include layout="@layout/content_main"/>

        <com.google.android.material.floatingactionbutton.FloatingActionButton
            android:id="@+id/fab"
            android:onClick="floatbuttonclick"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:gravity="bottom|end"
            android:layout_margin="@dimen/fab_margin"
            app:backgroundTint="@color/colorPrimary"
            app:srcCompat="@drawable/ic_edit_white_24dp"/>

    </androidx.coordinatorlayout.widget.CoordinatorLayout>
</code>```

AndroidManifest.xml

```<code><?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.example.spammessagedetector">

    <application
        android:allowBackup="true"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:roundIcon="@mipmap/ic_launcher_round"
        android:supportsRtl="true"
        android:theme="@style/AppTheme.NoActionBar">
        <!-- <activity android:name=".Inbox"></activity> -->
        <activity android:name=".MainActivity" />
        <activity android:name=".Profile" />
        <activity android:name=".Splash" />
        <activity android:name=".Inbox">

            <!-- android:theme="@style/splash" -->
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>

</manifest>
</code>```

答: by adding internet permission and removing setContentView(R.layout.activity_main); the code gets executed successfully.</p>

Body:
  E/AndroidRuntime: FATAL EXCEPTION: main
     Process: com.example.spammessagedetector, PID: 2137
     java.lang.RuntimeException: Unable to start activity ComponentInfo{com.example.spammessagedetector/com.example.spammessagedetector.Inbox}:
 java.lang.NullPointerException: Attempt to invoke virtual method 'void
 androidx.swiperefreshlayout.widget.SwipeRefreshLayout.setOnRefreshListener(androidx.swiperefreshlayout.widget.SwipeRefreshLayout$OnRefreshListener)'
 on a null object reference
         at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2646)
         at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2707)
         at android.app.ActivityThread.-wrap12(ActivityThread.java)
         at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1460)
         at android.os.Handler.dispatchMessage(Handler.java:102)
         at android.os.Looper.loop(Looper.java:154)
         at android.app.ActivityThread.main(ActivityThread.java:6077)
         at java.lang.reflect.Method.invoke(Native Method)
         at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:866)
         at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:756)
      Caused by: java.lang.NullPointerException: Attempt to invoke virtual method 'void
 androidx.swiperefreshlayout.widget.SwipeRefreshLayout.setOnRefreshListener(androidx.swiperefreshlayout.widget.SwipeRefreshLayout$OnRefreshListener)'
 on a null object reference
         at com.example.spammessagedetector.Inbox.onCreate(Inbox.java:76)
         at android.app.Activity.performCreate(Activity.java:6662)
         at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1118)
         at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2599)
         at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2707)
   at android.app.ActivityThread.-wrap12(ActivityThread.java)
         at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1460)
         at android.os.Handler.dispatchMessage(Handler.java:102)
         at android.os.Looper.loop(Looper.java:154)
         at android.app.ActivityThread.main(ActivityThread.java:6077)
         at java.lang.reflect.Method.invoke(Native Method)
         at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:866)
  at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:756)

here is the code for    Inbox.java

package com.example.spammessagedetector;

import androidx.appcompat.app.AppCompatActivity;
import androidx.appcompat.view.ActionMode;
import androidx.appcompat.widget.Toolbar;
import androidx.recyclerview.widget.DefaultItemAnimator;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import androidx.swiperefreshlayout.widget.SwipeRefreshLayout;

import android.os.Bundle;

import android.content.res.TypedArray;
import android.graphics.Color;
import android.os.Bundle;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.widget.Toast;
import java.util.ArrayList;
import java.util.List;

import com.example.spammessagedetector.R;
import com.example.spammessagedetector.adapter.MessagesAdapter;
import com.example.spammessagedetector.helper.DividerItemDecoration;
import com.example.spammessagedetector.model.Message;
import com.example.spammessagedetector.network.ApiClient;
import com.example.spammessagedetector.network.ApiInterface;
import com.google.android.material.floatingactionbutton.FloatingActionButton;
import com.google.android.material.snackbar.Snackbar;

import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;

public class Inbox extends AppCompatActivity implements SwipeRefreshLayout.OnRefreshListener, MessagesAdapter.MessageAdapterListener{

    private List<Message> messages = new ArrayList<>();
    private RecyclerView recyclerView;
    private MessagesAdapter mAdapter;
    private SwipeRefreshLayout swipeRefreshLayout;
    private ActionModeCallback actionModeCallback;
    private ActionMode actionMode;

    @Override
    protected void onCreate(Bundle savedInstanceState) {

        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_inbox);
        setContentView(R.layout.activity_main);
        Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
        setSupportActionBar(toolbar);

        FloatingActionButton fab = (FloatingActionButton) findViewById(R.id.fab);
        if (fab != null)
        fab.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                Snackbar.make(view, "Replace with your own action", Snackbar.LENGTH_LONG)
                        .setAction("Action", null).show();
            }
        });

        recyclerView = (RecyclerView) findViewById(R.id.recycler_view);
        swipeRefreshLayout = (SwipeRefreshLayout) findViewById(R.id.swipe_refresh_layout);
        swipeRefreshLayout.setOnRefreshListener(this);

        mAdapter = new MessagesAdapter(this, messages, this);
        RecyclerView.LayoutManager mLayoutManager = new LinearLayoutManager(getApplicationContext());
        recyclerView.setLayoutManager(mLayoutManager);
        recyclerView.setItemAnimator(new DefaultItemAnimator());
        recyclerView.addItemDecoration(new DividerItemDecoration(this, LinearLayoutManager.VERTICAL));
        recyclerView.setAdapter(mAdapter);

        actionModeCallback = new ActionModeCallback();

        // show loader and fetch messages
        swipeRefreshLayout.post(
                new Runnable() {
                    @Override
                    public void run() {
                        getInbox();
                    }
                }
        );
    }

    /**
     * Fetches mail messages by making HTTP request
     * url: https://api.androidhive.info/json/inbox.json
     */
    private void getInbox() {
        swipeRefreshLayout.setRefreshing(true);

        ApiInterface apiService =
                ApiClient.getClient().create(ApiInterface.class);

        Call<List<Message>> call = apiService.getInbox();
        call.enqueue(new Callback<List<Message>>() {
            @Override
            public void onResponse(Call<List<Message>> call, Response<List<Message>> response) {
                // clear the inbox
                messages.clear();

                // add all the messages
                // messages.addAll(response.body());

                // TODO - avoid looping
                // the loop was performed to add colors to each message
                for (Message message : response.body()) {
                    // generate a random color
                    message.setColor(getRandomMaterialColor("400"));
                    messages.add(message);
                }

                mAdapter.notifyDataSetChanged();
                swipeRefreshLayout.setRefreshing(false);
            }

            @Override
            public void onFailure(Call<List<Message>> call, Throwable t) {
                Toast.makeText(getApplicationContext(), "Unable to fetch json: " + t.getMessage(), Toast.LENGTH_LONG).show();
                swipeRefreshLayout.setRefreshing(false);
            }
        });
    }

    /**
     * chooses a random color from array.xml
     */
    private int getRandomMaterialColor(String typeColor) {
        int returnColor = Color.GRAY;
        int arrayId = getResources().getIdentifier("mdcolor_" + typeColor, "array", getPackageName());

        if (arrayId != 0) {
            TypedArray colors = getResources().obtainTypedArray(arrayId);
            int index = (int) (Math.random() * colors.length());
            returnColor = colors.getColor(index, Color.GRAY);
            colors.recycle();
        }
        return returnColor;
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.menu_main, menu);
        return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        // Handle action bar item clicks here. The action bar will
        // automatically handle clicks on the Home/Up button, so long
        // as you specify a parent activity in AndroidManifest.xml.
        int id = item.getItemId();

        //noinspection SimplifiableIfStatement
        if (id == R.id.action_search) {
            Toast.makeText(getApplicationContext(), "Search...", Toast.LENGTH_SHORT).show();
            return true;
        }

        return super.onOptionsItemSelected(item);
    }

    @Override
    public void onRefresh() {
        // swipe refresh is performed, fetch the messages again
        getInbox();
    }

    @Override
    public void onIconClicked(int position) {
        if (actionMode == null) {
            actionMode = startSupportActionMode(actionModeCallback);
        }

        toggleSelection(position);
    }

    @Override
    public void onIconImportantClicked(int position) {
        // Star icon is clicked,
        // mark the message as important
        Message message = messages.get(position);
        message.setImportant(!message.isImportant());
        messages.set(position, message);
        mAdapter.notifyDataSetChanged();
    }

    @Override
    public void onMessageRowClicked(int position) {
        // verify whether action mode is enabled or not
        // if enabled, change the row state to activated
        if (mAdapter.getSelectedItemCount() > 0) {
            enableActionMode(position);
        } else {
            // read the message which removes bold from the row
            Message message = messages.get(position);
            message.setRead(true);
            messages.set(position, message);
            mAdapter.notifyDataSetChanged();

            Toast.makeText(getApplicationContext(), "Read: " + message.getMessage(), Toast.LENGTH_SHORT).show();
        }
    }

    @Override
    public void onRowLongClicked(int position) {
        // long press is performed, enable action mode
        enableActionMode(position);
    }

    private void enableActionMode(int position) {
        if (actionMode == null) {
            actionMode = startSupportActionMode(actionModeCallback);
        }
        toggleSelection(position);
    }

    private void toggleSelection(int position) {
        mAdapter.toggleSelection(position);
        int count = mAdapter.getSelectedItemCount();

        if (count == 0) {
            actionMode.finish();
        } else {
            actionMode.setTitle(String.valueOf(count));
            actionMode.invalidate();
        }
    }

    private class ActionModeCallback implements ActionMode.Callback {
        @Override
        public boolean onCreateActionMode(ActionMode mode, Menu menu) {
            mode.getMenuInflater().inflate(R.menu.menu_action_mode, menu);

            // disable swipe refresh if action mode is enabled
            swipeRefreshLayout.setEnabled(false);
            return true;
        }

        @Override
        public boolean onPrepareActionMode(ActionMode mode, Menu menu) {
            return false;
        }

        @Override
        public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
            switch (item.getItemId()) {
                case R.id.action_delete:
                    // delete all the selected messages
                    deleteMessages();
                    mode.finish();
                    return true;

                default:
                    return false;
            }
        }

        @Override
        public void onDestroyActionMode(ActionMode mode) {
            mAdapter.clearSelections();
            swipeRefreshLayout.setEnabled(true);
            actionMode = null;
            recyclerView.post(new Runnable() {
                @Override
                public void run() {
                    mAdapter.resetAnimationIndex();
                    // mAdapter.notifyDataSetChanged();
                }
            });
        }
    }

    // deleting the messages from recycler view
    private void deleteMessages() {
        mAdapter.resetAnimationIndex();
        List<Integer> selectedItemPositions =
                mAdapter.getSelectedItems();
        for (int i = selectedItemPositions.size() - 1; i >= 0; i--) {
            mAdapter.removeData(selectedItemPositions.get(i));
        }
        mAdapter.notifyDataSetChanged();
    }
}

activity_inbox.xml

     <?xml version="1.0" encoding="utf-8"?>
    <androidx.coordinatorlayout.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:app="http://schemas.android.com/apk/res-auto"
        xmlns:tools="http://schemas.android.com/tools"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        tools:mContext=".Inbox">

        <com.google.android.material.appbar.AppBarLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:theme="@style/AppTheme.AppBarOverlay">

            <androidx.appcompat.widget.Toolbar
                android:id="@+id/toolbar"
                android:layout_width="match_parent"
                android:layout_height="?attr/actionBarSize"
                android:background="?attr/colorPrimary"
                app:popupTheme="@style/AppTheme.PopupOverlay"/>
        </com.google.android.material.appbar.AppBarLayout>

        <include layout="@layout/content_main"/>

        <com.google.android.material.floatingactionbutton.FloatingActionButton
            android:id="@+id/fab"
            android:onClick="floatbuttonclick"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:gravity="bottom|end"
            android:layout_margin="@dimen/fab_margin"
            app:backgroundTint="@color/colorPrimary"
            app:srcCompat="@drawable/ic_edit_white_24dp"/>

    </androidx.coordinatorlayout.widget.CoordinatorLayout>

AndroidManifest.xml

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.example.spammessagedetector">

    <application
        android:allowBackup="true"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:roundIcon="@mipmap/ic_launcher_round"
        android:supportsRtl="true"
        android:theme="@style/AppTheme.NoActionBar">

        <activity android:name=".MainActivity" />
        <activity android:name=".Profile" />
        <activity android:name=".Splash" />
        <activity android:name=".Inbox">

            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>

</manifest>


问:
Array filter is not returning correct for Zero?

function zeroCount(arr){
   const zero = arr.filter(el=>{
            if(el===0){
                return el ;
            }
        });
    return zero.length ; // but it returns 0. I want it to return 3.
}

console.log(zeroCount([2,3,0,5,0,2,0]));```

I want to return the no. of zero present in the array using filter.

答:
filter callback function should return boolean and you're not handling the false case

Your function should look like this

```<code>function zeroCount(arr){
  const zero = arr.filter(el=>{
     return el === 0;
  });

  return zero.length; // it returns 3
}
</code>```

or using shorthand

```<code>function zeroCount(arr){
  const zero = arr.filter(el=> el === 0);

  return zero.length; // it returns 3
}

</code>```

Body:
function zeroCount(arr){
   const zero = arr.filter(el=>{
            if(el===0){
                return el ;
            }
        });
    return zero.length ; // but it returns 0. I want it to return 3.
}

console.log(zeroCount([2,3,0,5,0,2,0]));

I want to return the no. of zero present in the array using filter.

Body:
filter callback function should return boolean and you're not handling the false case

Your function should look like this

function zeroCount(arr){
  const zero = arr.filter(el=>{
     return el === 0;
  });

  return zero.length; // it returns 3
}

or using shorthand

function zeroCount(arr){
  const zero = arr.filter(el=> el === 0);

  return zero.length; // it returns 3
}


答:
Filter will only add the element if you return a "truthy" value. Currently, you are returning e1, with is 0. (This is falsy).

Just return true instead.

function zeroCount(arr) {
  const zero = arr.filter(el => {
    if (el === 0) {
      return true;
    }
  });
  return zero.length; // but it returns 0. I want it to return 3.
}

console.log(zeroCount([2, 3, 0, 5, 0, 2, 0]));```

Title: Array filter is not returning correct for Zero?


问:
PHPMailer + reCAPTCHA or any other anti-spam - problem
I've made a contact form on my friends website and everything works correctly but he gets a lot of spam offers like bitcoins/porn etc. I tried to setup reCAPTCHA but that didn't work.

I'm using PHPMailer (previous I used google API for mail but that kind of form gets a lot more spam offers) and I can't find a way to protect against bots.

I'm wondering - maybe that the mailer script is running in background after pushing the submit button is the problem? Maybe that's why it skipping the reCAPTCHA.

I tried everything - changing the max length of inputs, their names... my last try was this recaptcha:

https://github.com/anhskohbo/no-captcha

My code:

TOP of the index.php:

```<code>    <?php
require_once "vendor/autoload.php";

$secret  = '*****';
$sitekey = '*****';
$captcha = new \Anhskohbo\NoCaptcha\NoCaptcha($secret, $sitekey);

if ( isset($_POST['submit'])) {
    if($captcha->verifyResponse($_POST['g-recaptcha-response'])) {
        //proceed further
    } else {
        echo "Incorrect captcha";
    }
}
?>
</code>```

My form:

```<code> <form name="test" role="form" action="sendmail.php" method="POST" onSubmit="alert('Dziękujemy za kontakt :)'); window.location.reload();"  >

        <div class="row">
            <div class="col span-1-of-3">
                <label>Imię i nazwisko:</label>
            </div>
            <div class="col span-2-of-3">
            <input maxlength="30" name="a1" required="required" type="text"  placeholder="Imię i nazwisko" required/>
            </div>
        </div>
        <div class="row">
            <div class="col span-1-of-3">
            <label>E-mail:</label>
            </div>
            <div class="col span-2-of-3">
            <input maxlength="30" name="a2" required="required" type="email" placeholder="E-mail" required/>
            </div>
        </div>
        <div class="row">
            <div class="col span-1-of-3">
            <label>Telefon:</label>
            </div>
            <div class="col span-2-of-3">
            <input maxlength="30" name="a3" required="required" type="text" placeholder="Numer telefonu"  required/>
            </div>
        </div>

        <div class="row">
            <div class="col span-1-of-3">
            <label>Temat:</label>
            </div>
            <div class="col span-2-of-3">
            <input maxlength="30" name="a4" required="required" type="text" placeholder="Temat wiadomości" required/>
            </div>
        </div>

        <div class="row">
            <div class="col span-1-of-3">
            <label>Wiadomość:</label>
            </div>
            <div class="col span-2-of-3">
            <textarea name="a5" placeholder="Wiadomość"></textarea>
            </div>
        </div>

        <div class="row">
            <div class="col span-1-of-3">
            <label> </label>
            </div>
            <div class="col span-2-of-3">
            <?php echo $captcha->display(); ?>
            <input name="myFormSubmitted" type="submit" value="Wyślij" style="margin-top:10px;">
            </div>
        </div>

    </form>
    <?php echo $captcha->renderJs(); ?>
</code>```

Sendmail.php :

```<code>    <?php
/**
 * This example shows settings to use when sending via Google's Gmail servers.
 * This uses traditional id & password authentication - look at the gmail_xoauth.phps
 * example to see how to use XOAUTH2.
 * The IMAP section shows how to save this message to the 'Sent Mail' folder using IMAP commands.
 */

//Import PHPMailer classes into the global namespace
use PHPMailer\PHPMailer\PHPMailer;
use PHPMailer\PHPMailer\SMTP;
use FormGuide\Handlx\FormHandler;

require 'vendor/autoload.php';

//Create a new PHPMailer instance
$mail = new PHPMailer;

//Tell PHPMailer to use SMTP
$mail->isSMTP();

//Enable SMTP debugging
// SMTP::DEBUG_OFF = off (for production use)
// SMTP::DEBUG_CLIENT = client messages
// SMTP::DEBUG_SERVER = client and server messages
$mail->SMTPDebug = SMTP::DEBUG_SERVER;

//Set the hostname of the mail server
$mail->Host = 'smtp.gmail.com';
// use
// $mail->Host = gethostbyname('smtp.gmail.com');
// if your network does not support SMTP over IPv6

//Set the SMTP port number - 587 for authenticated TLS, a.k.a. RFC4409 SMTP submission
$mail->Port = 587;

$mail->CharSet = "UTF-8";
//Set the encryption mechanism to use - STARTTLS or SMTPS
$mail->SMTPSecure = PHPMailer::ENCRYPTION_STARTTLS;

//Whether to use SMTP authentication
$mail->SMTPAuth = true;

//Username to use for SMTP authentication - use full email address for gmail
$mail->Username = '*****';

//Password to use for SMTP authentication
$mail->Password = '*****';

//Set who the message is to be sent from
$mail->setFrom('from@example.com');

//Set an alternative reply-to address
$mail->addReplyTo( $_POST['mail']);

//Set who the message is to be sent to
$mail->addAddress('****');

$mail->IsHTML(true);

if ($mail->addReplyTo($_POST['a2'], $_POST['a1'])) {
    $mail->Subject = 'Formularz kontaktowy - Cargo-trans.biz';
    //Keep it simple - don't use HTML
    //$mail->isHTML(false);
    //Build a simple message body
    $mail->Body = <<<EOT

<p style="margin-bottom:10px;"><b>Imię i naziwsko:</b> {$_POST['a1']} </p>
<br>
<p style="margin-bottom:10px;"><b>E-mail:</b> {$_POST['a2']} </p>
<br>
<p style="margin-bottom:10px;"><b>Telefon kontaktowy:</b> {$_POST['a3']} </p>
<br>
<p style="margin-bottom:10px;"><b>Temat:</b> {$_POST['a4']} </p>
<br>
<p style="margin-bottom:10px;"><b>Wiadomość:</b> {$_POST['a5']} </p>
<br>
<img src = "http://cargo-trans.biz/resources/img/napis.png" style="margin-top:10px;">
EOT;
    //Send the message, check for errors
    if (!$mail->send()) {
        //The reason for failing to send will be in $mail->ErrorInfo
        //but you shouldn't display errors to users - process the error, log it on your server.
        $msg = 'Sorry, something went wrong. Please try again later.';
    } else {
        $msg = 'Message sent! Thanks for contacting us.';
    }
} else {
    $msg = 'Invalid email address, message ignored.';
}

?>
</code>```

答:
I would improve the script by adding an encoding check before sending - for example like this:

```<code>iconv("UTF-8", "UTF-8//IGNORE", $subject_or_message_or_any_string);
</code>```

also I wouldn't display the info if the mail failed to send instead of that I would rather use something like:

```<code> if (!$mail->Send())
 {
   LogErrorMessage("Mailer Error: %s", $mail->ErrorInfo);
  die ("Sorry, mail could not be sent");
}
</code>```

Next I would send or log IP address of user that sent the email form - for cases he likes to spam, you can block him easily.

Body:
I've made a contact form on my friends website and everything works correctly but he gets a lot of spam offers like bitcoins/porn etc. I tried to setup reCAPTCHA but that didn't work.

I'm using PHPMailer (previous I used google API for mail but that kind of form gets a lot more spam offers) and I can't find a way to protect against bots.

I'm wondering - maybe that the mailer script is running in background after pushing the submit button is the problem? Maybe that's why it skipping the reCAPTCHA.

I tried everything - changing the max length of inputs, their names... my last try was this recaptcha:

https://github.com/anhskohbo/no-captcha

My code:

TOP of the index.php:

    <?php
require_once "vendor/autoload.php";

$secret  = '*****';
$sitekey = '*****';
$captcha = new \Anhskohbo\NoCaptcha\NoCaptcha($secret, $sitekey);

if ( isset($_POST['submit'])) {
    if($captcha->verifyResponse($_POST['g-recaptcha-response'])) {
        //proceed further
    } else {
        echo "Incorrect captcha";
    }
}
?>

My form:

 <form name="test" role="form" action="sendmail.php" method="POST" onSubmit="alert('Dziękujemy za kontakt :)'); window.location.reload();"  >

                Imię i nazwisko:

            <input maxlength="30" name="a1" required="required" type="text"  placeholder="Imię i nazwisko" required/>

            E-mail:

            <input maxlength="30" name="a2" required="required" type="email" placeholder="E-mail" required/>

            Telefon:

            <input maxlength="30" name="a3" required="required" type="text" placeholder="Numer telefonu"  required/>

            Temat:

            <input maxlength="30" name="a4" required="required" type="text" placeholder="Temat wiadomości" required/>

            Wiadomość:

            <textarea name="a5" placeholder="Wiadomość"></textarea>

            <?php echo $captcha->display(); ?>
            <input name="myFormSubmitted" type="submit" value="Wyślij" style="margin-top:10px;">

    </form>
    <?php echo $captcha->renderJs(); ?>

Sendmail.php :

    <?php
/**
 * This example shows settings to use when sending via Google's Gmail servers.
 * This uses traditional id & password authentication - look at the gmail_xoauth.phps
 * example to see how to use XOAUTH2.
 * The IMAP section shows how to save this message to the 'Sent Mail' folder using IMAP commands.
 */

//Import PHPMailer classes into the global namespace
use PHPMailer\PHPMailer\PHPMailer;
use PHPMailer\PHPMailer\SMTP;
use FormGuide\Handlx\FormHandler;

require 'vendor/autoload.php';

//Create a new PHPMailer instance
$mail = new PHPMailer;

//Tell PHPMailer to use SMTP
$mail->isSMTP();

//Enable SMTP debugging
// SMTP::DEBUG_OFF = off (for production use)
// SMTP::DEBUG_CLIENT = client messages
// SMTP::DEBUG_SERVER = client and server messages
$mail->SMTPDebug = SMTP::DEBUG_SERVER;

//Set the hostname of the mail server
$mail->Host = 'smtp.gmail.com';
// use
// $mail->Host = gethostbyname('smtp.gmail.com');
// if your network does not support SMTP over IPv6

//Set the SMTP port number - 587 for authenticated TLS, a.k.a. RFC4409 SMTP submission
$mail->Port = 587;

$mail->CharSet = "UTF-8";
//Set the encryption mechanism to use - STARTTLS or SMTPS
$mail->SMTPSecure = PHPMailer::ENCRYPTION_STARTTLS;

//Whether to use SMTP authentication
$mail->SMTPAuth = true;

//Username to use for SMTP authentication - use full email address for gmail
$mail->Username = '*****';

//Password to use for SMTP authentication
$mail->Password = '*****';

//Set who the message is to be sent from
$mail->setFrom('from@example.com');

//Set an alternative reply-to address
$mail->addReplyTo( $_POST['mail']);

//Set who the message is to be sent to
$mail->addAddress('****');

$mail->IsHTML(true);

if ($mail->addReplyTo($_POST['a2'], $_POST['a1'])) {
    $mail->Subject = 'Formularz kontaktowy - Cargo-trans.biz';
    //Keep it simple - don't use HTML
    //$mail->isHTML(false);
    //Build a simple message body
    $mail->Body = <<<EOT

Imię i naziwsko: {$_POST['a1']}

E-mail: {$_POST['a2']}

Telefon kontaktowy: {$_POST['a3']}

Temat: {$_POST['a4']}

Wiadomość: {$_POST['a5']}

EOT;
    //Send the message, check for errors
    if (!$mail->send()) {
        //The reason for failing to send will be in $mail->ErrorInfo
        //but you shouldn't display errors to users - process the error, log it on your server.
        $msg = 'Sorry, something went wrong. Please try again later.';
    } else {
        $msg = 'Message sent! Thanks for contacting us.';
    }
} else {
    $msg = 'Invalid email address, message ignored.';
}

?>

Body:
I would improve the script by adding an encoding check before sending - for example like this:

iconv("UTF-8", "UTF-8//IGNORE", $subject_or_message_or_any_string);

also I wouldn't display the info if the mail failed to send instead of that I would rather use something like:

 if (!$mail->Send())
 {
   LogErrorMessage("Mailer Error: %s", $mail->ErrorInfo);
  die ("Sorry, mail could not be sent");
}

Next I would send or log IP address of user that sent the email form - for cases he likes to spam, you can block him easily.


问:
SwiftUI mutiple bindings
I am having a MasterView Controller which contains a List and my Detail View Controller. The Detail View Controller will edit information about the dataset selected in MasterView.

As far as I understand, I will have to create a Binding in my Detail, so when I edit details, the details should change in my MasterView list aswell.

What is correct way of doing this? My detail view consist of multiple views aswell, where the edit is made. Do I have to push the information with a binding to all my lower views? Can I go from @State -> @Binding -> @Binding and still the first state will change?

I am using SwiftUI for MacOS.

That is how it looks (left the List View and right the Edit View)

答:
for anything more complex as simple State / Binding to visually change some components of your UI, go ahead and use @ObservableObject / @ObservedObject or for really global sharing @EnviromentObject instead @State / @Binding. Put all the logic to your model, don't try to do it in your SwiftUI. It will save you a lot of trouble, bug finding etc.

UPDATE there is no better way than see the documentation

```<code>/// A linked View property that reads a `ObservableObject` supplied by an
/// ancestor view that will automatically invalidate its view when the object
/// changes.
///
/// - Precondition: A model must be provided on an ancestor view by calling
///     `environmentObject(_:)`.
@available(iOS 13.0, OSX 10.15, tvOS 13.0, watchOS 6.0, *)
@propertyWrapper public struct EnvironmentObject<ObjectType> : DynamicProperty where ObjectType : ObservableObject {

    /// A wrapper of the underlying `ObservableObject` that can create
    /// `Binding`s to its properties using dynamic member lookup.
    @dynamicMemberLookup public struct Wrapper {

        /// Creates a `Binding` to a value semantic property of a
        /// reference type.
        ///
        /// If `Value` is not value semantic, the updating behavior for
        /// any views that make use of the resulting `Binding` is
        /// unspecified.
        public subscript<Subject>(dynamicMember keyPath: ReferenceWritableKeyPath<ObjectType, Subject>) -> Binding<Subject> { get }
    }

    /// The current model supplied by an ancestor view.
    @inlinable public var wrappedValue: ObjectType { get }

    public var projectedValue: EnvironmentObject<ObjectType>.Wrapper { get }

    public init()
}
</code>```

Use it if all @Published properties, computed properties etc. are shared widely.

If the model is related only to subset of your Views, use Observable / Observed instead. There is a lot of tutorials and even some nice examples on stackoverflow how to use it.

```<code>/// A dynamic view property that subscribes to a `ObservableObject` automatically invalidating the view
/// when it changes.
@available(iOS 13.0, OSX 10.15, tvOS 13.0, watchOS 6.0, *)
@propertyWrapper public struct ObservedObject<ObjectType> : DynamicProperty where ObjectType : ObservableObject {

    /// A wrapper of the underlying `ObservableObject` that can create
    /// `Binding`s to its properties using dynamic member lookup.
    @dynamicMemberLookup public struct Wrapper {

        /// Creates a `Binding` to a value semantic property of a
        /// reference type.
        ///
        /// If `Value` is not value semantic, the updating behavior for
        /// any views that make use of the resulting `Binding` is
        /// unspecified.
        public subscript<Subject>(dynamicMember keyPath: ReferenceWritableKeyPath<ObjectType, Subject>) -> Binding<Subject> { get }
    }

    public init(initialValue: ObjectType)

    public init(wrappedValue: ObjectType)

    public var wrappedValue: ObjectType

    public var projectedValue: ObservedObject<ObjectType>.Wrapper { get }
}
</code>```

and finally you need some model, which has to conform to

```<code>/// A type of object with a publisher that emits before the object has changed.
///
/// By default an `ObservableObject` will synthesize an `objectWillChange`
/// publisher that emits before any of its `@Published` properties changes:
///
///     class Contact: ObservableObject {
///         @Published var name: String
///         @Published var age: Int
///
///         init(name: String, age: Int) {
///             self.name = name
///             self.age = age
///         }
///
///         func haveBirthday() -> Int {
///             age += 1
///             return age
///         }
///     }
///
///     let john = Contact(name: "John Appleseed", age: 24)
///     john.objectWillChange.sink { _ in print("\(john.age) will change") }
///     print(john.haveBirthday())
///     // Prints "24 will change"
///     // Prints "25"
///
@available(iOS 13.0, OSX 10.15, tvOS 13.0, watchOS 6.0, *)
public protocol ObservableObject : AnyObject {

    /// The type of publisher that emits before the object has changed.
    associatedtype ObjectWillChangePublisher : Publisher = ObservableObjectPublisher where Self.ObjectWillChangePublisher.Failure == Never

    /// A publisher that emits before the object has changed.
    var objectWillChange: Self.ObjectWillChangePublisher { get }
}

@available(iOS 13.0, OSX 10.15, tvOS 13.0, watchOS 6.0, *)
extension ObservableObject where Self.ObjectWillChangePublisher == ObservableObjectPublisher {

    /// A publisher that emits before the object has changed.
    public var objectWillChange: ObservableObjectPublisher { get }
}
</code>```

Title: SwiftUI mutiple bindings

Body:
for anything more complex as simple State / Binding to visually change some components of your UI, go ahead and use @ObservableObject / @ObservedObject or for really global sharing @EnviromentObject instead @State / @Binding. Put all the logic to your model, don't try to do it in your SwiftUI. It will save you a lot of trouble, bug finding etc.

UPDATE there is no better way than see the documentation

/// A linked View property that reads a `ObservableObject` supplied by an
/// ancestor view that will automatically invalidate its view when the object
/// changes.
///
/// - Precondition: A model must be provided on an ancestor view by calling
///     `environmentObject(_:)`.
@available(iOS 13.0, OSX 10.15, tvOS 13.0, watchOS 6.0, *)
@propertyWrapper public struct EnvironmentObject<ObjectType> : DynamicProperty where ObjectType : ObservableObject {

    /// A wrapper of the underlying `ObservableObject` that can create
    /// `Binding`s to its properties using dynamic member lookup.
    @dynamicMemberLookup public struct Wrapper {

        /// Creates a `Binding` to a value semantic property of a
        /// reference type.
        ///
        /// If `Value` is not value semantic, the updating behavior for
        /// any views that make use of the resulting `Binding` is
        /// unspecified.
        public subscript<Subject>(dynamicMember keyPath: ReferenceWritableKeyPath<ObjectType, Subject>) -> Binding<Subject> { get }
    }

    /// The current model supplied by an ancestor view.
    @inlinable public var wrappedValue: ObjectType { get }

    public var projectedValue: EnvironmentObject<ObjectType>.Wrapper { get }

    public init()
}

Use it if all @Published properties, computed properties etc. are shared widely.

If the model is related only to subset of your Views, use Observable / Observed instead. There is a lot of tutorials and even some nice examples on stackoverflow how to use it.

/// A dynamic view property that subscribes to a `ObservableObject` automatically invalidating the view
/// when it changes.
@available(iOS 13.0, OSX 10.15, tvOS 13.0, watchOS 6.0, *)
@propertyWrapper public struct ObservedObject<ObjectType> : DynamicProperty where ObjectType : ObservableObject {

    /// A wrapper of the underlying `ObservableObject` that can create
    /// `Binding`s to its properties using dynamic member lookup.
    @dynamicMemberLookup public struct Wrapper {

        /// Creates a `Binding` to a value semantic property of a
        /// reference type.
        ///
        /// If `Value` is not value semantic, the updating behavior for
        /// any views that make use of the resulting `Binding` is
        /// unspecified.
        public subscript<Subject>(dynamicMember keyPath: ReferenceWritableKeyPath<ObjectType, Subject>) -> Binding<Subject> { get }
    }

    public init(initialValue: ObjectType)

    public init(wrappedValue: ObjectType)

    public var wrappedValue: ObjectType

    public var projectedValue: ObservedObject<ObjectType>.Wrapper { get }
}

and finally you need some model, which has to conform to

/// A type of object with a publisher that emits before the object has changed.
///
/// By default an `ObservableObject` will synthesize an `objectWillChange`
/// publisher that emits before any of its `@Published` properties changes:
///
///     class Contact: ObservableObject {
///         @Published var name: String
///         @Published var age: Int
///
///         init(name: String, age: Int) {
///             self.name = name
///             self.age = age
///         }
///
///         func haveBirthday() -> Int {
///             age += 1
///             return age
///         }
///     }
///
///     let john = Contact(name: "John Appleseed", age: 24)
///     john.objectWillChange.sink { _ in print("\(john.age) will change") }
///     print(john.haveBirthday())
///     // Prints "24 will change"
///     // Prints "25"
///
@available(iOS 13.0, OSX 10.15, tvOS 13.0, watchOS 6.0, *)
public protocol ObservableObject : AnyObject {

    /// The type of publisher that emits before the object has changed.
    associatedtype ObjectWillChangePublisher : Publisher = ObservableObjectPublisher where Self.ObjectWillChangePublisher.Failure == Never

    /// A publisher that emits before the object has changed.
    var objectWillChange: Self.ObjectWillChangePublisher { get }
}

@available(iOS 13.0, OSX 10.15, tvOS 13.0, watchOS 6.0, *)
extension ObservableObject where Self.ObjectWillChangePublisher == ObservableObjectPublisher {

    /// A publisher that emits before the object has changed.
    public var objectWillChange: ObservableObjectPublisher { get }
}


答:
Right now you're returning 0 if the element is 0. How filter works is that is expects a boolean value on weither it should keep the current element in the new array.

The unlucky part here is that you're returning 0 which translates to false.

function zeroCount(arr){
   const zero = arr.filter(el=>{
            if(el===0){
                return el; // This returns 0 so it won't be added to the filtered array
            }
        });
    return zero.length ; // but it returns 0. I want it to return 3.
}

console.log(zeroCount([2,3,0,5,0,2,0]));```
</div>
</div>

<br><br>
This would work</p>

<p><div class="snippet" data-lang="js" data-hide="false" data-console="true" data-babel="false">
<div class="snippet-code">
<pre class="snippet-code-js lang-js prettyprint-override"><code>function zeroCount(arr){
   const zero = arr.filter(el=> el === 0); // if the element is 0 then el === 0 will resolve to true and the element will be added to the filer array
    return zero.length ; // returns 3
}

console.log(zeroCount([2,3,0,5,0,2,0]));</code>```

Body:
Right now you're returning 0 if the element is 0. How filter works is that is expects a boolean value on weither it should keep the current element in the new array.

The unlucky part here is that you're returning 0 which translates to false.

function zeroCount(arr){
   const zero = arr.filter(el=>{
            if(el===0){
                return el; // This returns 0 so it won't be added to the filtered array
            }
        });
    return zero.length ; // but it returns 0. I want it to return 3.
}

console.log(zeroCount([2,3,0,5,0,2,0]));

This would work

function zeroCount(arr){
   const zero = arr.filter(el=> el === 0); // if the element is 0 then el === 0 will resolve to true and the element will be added to the filer array
    return zero.length ; // returns 3
}

console.log(zeroCount([2,3,0,5,0,2,0]));


问:
Including Twitter Widgets.js via HTTPS
I'm having a minor problem with Mixed-content on HTTPS served pages on our site, when we include the http://platform.twitter.com/widgets.js

Apparently Twitter doesn't have a valid certificate -- but hopefully I am mistaken.

Do any of you have a solution to the problem. I've searched here and on google for a related problem, and have found:

Serve the file myself, via HTTPS (but this gives me something I'll need to maintain)

Exclude the file from my pages, when serving via HTTPS (which means I lose functionality)

Suggestions ?

Update

See resolution on accepted answer below.

答:
There is an easier workaround using PHP that requires no maintenance, unless Twitter changes their JS file location.

Create a PHP file in your JS folder, called twitter.platform.js.php or something along those lines. Paste the following into the file.

```<code><?php
header('Content-type: text/javascript');
echo file_get_contents('http://platform.twitter.com/widgets.js');
?>
</code>```

Then include the PHP script instead of Twitter's JS.

```<code><script type="text/javascript" src="/location/to/js/twitter.platform.js.php"></script>
</code>```

The above code will pull Twitter's non-secure JS from their server and render the output as JavaScript and allow you to serve it over SSL without the warnings, as it will originate from your site.

Update: The above workaround does, as @paul-mcmahon mentioned in the comments, cause SSL errors, when using the Twitter Follow button.

Title: Including Twitter Widgets.js via HTTPS

Body:
There is an easier workaround using PHP that requires no maintenance, unless Twitter changes their JS file location.

Create a PHP file in your JS folder, called twitter.platform.js.php or something along those lines. Paste the following into the file.

<?php
header('Content-type: text/javascript');
echo file_get_contents('http://platform.twitter.com/widgets.js');
?>

Then include the PHP script instead of Twitter's JS.

<script type="text/javascript" src="/location/to/js/twitter.platform.js.php"></script>

The above code will pull Twitter's non-secure JS from their server and render the output as JavaScript and allow you to serve it over SSL without the warnings, as it will originate from your site.

Update: The above workaround does, as @paul-mcmahon mentioned in the comments, cause SSL errors, when using the Twitter Follow button.


问:
Regex start with exactly two alphabetic characters and than followed by any digits
I'm trying to create a very simple regex that accepts strings:

starts with two [A-Za-z] characters

ends with any number of digits

my code is:

Regex.IsMatch("AA00000000000", $"^[A-Za-z]{2}[0-9]*$")
```

but it returns False. Where am I wrong? I've already tested the same regex with the same input on regexstorm.net and it works.

答:
Working for me with below code:</p>

```<code>string pattern = @"^[A-Za-z]{2}[0-9]*$";
string str = "AA00000000000";
bool val = Regex.IsMatch(str, pattern);
</code>```

Body:
I'm trying to create a very simple regex that accepts strings:

starts with two [A-Za-z] characters

ends with any number of digits

my code is:

Regex.IsMatch("AA00000000000", $"^[A-Za-z]{2}[0-9]*$")

but it returns False. Where am I wrong? I've already tested the same regex with the same input on regexstorm.net and it works.

Body:
Working for me with below code:

string pattern = @"^[A-Za-z]{2}[0-9]*$";
string str = "AA00000000000";
bool val = Regex.IsMatch(str, pattern);


问:
detecting continuous touched cells to win by collision or position
I  try to design (bee_cell_competition) for students in my school. Everything works in my code . I have 7*7 (49) cells as movie clips. Students select a random cell trying to make a continuous touched cells to win (vertically) as it declared in the picture. How can I get when the user touches a new cell (mc_47) and so that the user wins. I have this code but it cannot detect. See this image description </p>

```<code>var i =0;
var j =0;

var sellected_bee_cell;
var enemy1;
var enemy2;

var touched_cell_arr:Array = new Array(panel_bee.cell_0,panel_bee.cell_00);

var mc_bee_cells:Array = new Array(panel_bee.cell_1,panel_bee.cell_2,panel_bee.cell_3,panel_bee.cell_4,panel_bee.cell_5,panel_bee.cell_6,panel_bee.cell_7,panel_bee.cell_8,panel_bee.cell_9,panel_bee.cell_10,panel_bee.cell_11,panel_bee.cell_12,panel_bee.cell_13,panel_bee.cell_14,panel_bee.cell_15,panel_bee.cell_16,panel_bee.cell_17,panel_bee.cell_18,panel_bee.cell_19,panel_bee.cell_20,panel_bee.cell_21,panel_bee.cell_22,panel_bee.cell_23,panel_bee.cell_24,panel_bee.cell_25,panel_bee.cell_26,panel_bee.cell_27,panel_bee.cell_28,panel_bee.cell_29,panel_bee.cell_30,panel_bee.cell_31,panel_bee.cell_32,panel_bee.cell_33,panel_bee.cell_34,panel_bee.cell_35,panel_bee.cell_36,panel_bee.cell_37,panel_bee.cell_38,panel_bee.cell_39,panel_bee.cell_40,panel_bee.cell_41,panel_bee.cell_42,panel_bee.cell_43,panel_bee.cell_44,panel_bee.cell_45,panel_bee.cell_46,panel_bee.cell_47,panel_bee.cell_48,panel_bee.cell_49);
//====================================================================================

for (i = 0 ; i < 49 ; ++i)
{
        mc_bee_cells[i].buttonMode = true;
        mc_bee_cells[i].mouseChildren = false;
}

for (i = 0 ; i < 49 ; ++i)
{
    mc_bee_cells[i].addEventListener(MouseEvent.CLICK, run_the_next_q_4bee);

    function run_the_next_q_4bee(e:Event):void
    {
        sellected_bee_cell = e.currentTarget ;
        sellected_bee_cell.gotoAndStop("green");
        touched_cell_arr.push(sellected_bee_cell);
        check_win(null);
    }
}
//===========================================================

function check_win(e:Event):void
{
    for (var i:int = 0; i < touched_cell_arr.length - 1; i++)
    {
        var enemy1 = mc_bee_cells[i];

        for(var j:int = i+1; j< touched_cell_arr.length; j++)
        {
            var enemy2 = mc_bee_cells[j];

            if(enemy1.hitTestObject(enemy2))
            {
                trace("yes");
                // now i need how to check that user completed continuous touched cells vertically or horizontally
            }
        }
    }
}

//===========================================================
</code>```

答:
You should save chains of touched cells. You have to make refactoring for this purpose:

1) Create a class Cell which extends MovieClip for your cells:

```<code>public class Cell extends MovieClip {
    public var prevCell:Cell = null;
    public var nextCell:Cell = null;
    public var index:uint = 0;
    public var isSelected = false;

    public function Cell() {}
}
</code>```

2) Rewrite the run_the_next_q_4bee handler:

```<code>var neighbourSelectedCellIndex:Array = [];

function run_the_next_q_4bee(e:Event):void {
    sellected_bee_cell = e.currentTarget ;
    sellected_bee_cell.gotoAndStop("green");
    touched_cell_arr.push(sellected_bee_cell);

    // Check neighbour cells
    var neighbourSelectedCellIndex =
    checkNeighbourCells(sellected_bee_cell.index)
    if (neighbourSelectedCellIndex == -1) {
        touchedCellsChains.push(sellected_bee_cell)
    } else {
        var neighbourCell = mc_bee_cells[neighbourSelectedCellIndex];
        neighbourCell.nextCell = sellected_bee_cell;
        sellected_bee_cell.prevCell = prevCell;
    }

    check_win(null);
}

function checkNeighbourCells(selectedCellIndex:uint):int {
    // Check neighbour cells. Are there any selected adjoining cell?
    // If there is any selected cell return its index
    return <selected cell index>;
    // If there is no selected cell return -1
    return -1;
}
</code>```

3) Rewrite the check_win method:

```<code>// You make call `hitTestObject` method
var hasTop = false;
var hasBottom = false;

var prevCell = enemy1;
do {
    if (prevCell.index < 7) {
        hasTop = true;
    } else if (prevCell.index > 42) {
        hasBottom = true;
    }

    prevCell = prevCell.prevCell;
} while (!prevCell)

var nextCell = enemy1;
do {
    if (nextCell.index < 7) {
        hasTop = true;
    } else if (nextCell.index > 42) {
        hasBottom = true;
    }

    nextCell = nextCell.nextCell;
} while (!nextCell)

if (hasTop && hasBottom) {
    trace("You win!");
}
</code>```

Body:
I  try to design (bee_cell_competition) for students in my school. Everything works in my code . I have 7*7 (49) cells as movie clips. Students select a random cell trying to make a continuous touched cells to win (vertically) as it declared in the picture. How can I get when the user touches a new cell (mc_47) and so that the user wins. I have this code but it cannot detect. See this image description

var i =0;
var j =0;

var sellected_bee_cell;
var enemy1;
var enemy2;

var touched_cell_arr:Array = new Array(panel_bee.cell_0,panel_bee.cell_00);

var mc_bee_cells:Array = new Array(panel_bee.cell_1,panel_bee.cell_2,panel_bee.cell_3,panel_bee.cell_4,panel_bee.cell_5,panel_bee.cell_6,panel_bee.cell_7,panel_bee.cell_8,panel_bee.cell_9,panel_bee.cell_10,panel_bee.cell_11,panel_bee.cell_12,panel_bee.cell_13,panel_bee.cell_14,panel_bee.cell_15,panel_bee.cell_16,panel_bee.cell_17,panel_bee.cell_18,panel_bee.cell_19,panel_bee.cell_20,panel_bee.cell_21,panel_bee.cell_22,panel_bee.cell_23,panel_bee.cell_24,panel_bee.cell_25,panel_bee.cell_26,panel_bee.cell_27,panel_bee.cell_28,panel_bee.cell_29,panel_bee.cell_30,panel_bee.cell_31,panel_bee.cell_32,panel_bee.cell_33,panel_bee.cell_34,panel_bee.cell_35,panel_bee.cell_36,panel_bee.cell_37,panel_bee.cell_38,panel_bee.cell_39,panel_bee.cell_40,panel_bee.cell_41,panel_bee.cell_42,panel_bee.cell_43,panel_bee.cell_44,panel_bee.cell_45,panel_bee.cell_46,panel_bee.cell_47,panel_bee.cell_48,panel_bee.cell_49);
//====================================================================================

for (i = 0 ; i < 49 ; ++i)
{
        mc_bee_cells[i].buttonMode = true;
        mc_bee_cells[i].mouseChildren = false;
}

for (i = 0 ; i < 49 ; ++i)
{
    mc_bee_cells[i].addEventListener(MouseEvent.CLICK, run_the_next_q_4bee);

    function run_the_next_q_4bee(e:Event):void
    {
        sellected_bee_cell = e.currentTarget ;
        sellected_bee_cell.gotoAndStop("green");
        touched_cell_arr.push(sellected_bee_cell);
        check_win(null);
    }
}
//===========================================================

function check_win(e:Event):void
{
    for (var i:int = 0; i < touched_cell_arr.length - 1; i++)
    {
        var enemy1 = mc_bee_cells[i];

        for(var j:int = i+1; j< touched_cell_arr.length; j++)
        {
            var enemy2 = mc_bee_cells[j];

            if(enemy1.hitTestObject(enemy2))
            {
                trace("yes");
                // now i need how to check that user completed continuous touched cells vertically or horizontally
            }
        }
    }
}

//===========================================================

Body:
You should save chains of touched cells. You have to make refactoring for this purpose:

1) Create a class Cell which extends MovieClip for your cells:

public class Cell extends MovieClip {
    public var prevCell:Cell = null;
    public var nextCell:Cell = null;
    public var index:uint = 0;
    public var isSelected = false;

    public function Cell() {}
}

2) Rewrite the run_the_next_q_4bee handler:

var neighbourSelectedCellIndex:Array = [];

function run_the_next_q_4bee(e:Event):void {
    sellected_bee_cell = e.currentTarget ;
    sellected_bee_cell.gotoAndStop("green");
    touched_cell_arr.push(sellected_bee_cell);

    // Check neighbour cells
    var neighbourSelectedCellIndex =
    checkNeighbourCells(sellected_bee_cell.index)
    if (neighbourSelectedCellIndex == -1) {
        touchedCellsChains.push(sellected_bee_cell)
    } else {
        var neighbourCell = mc_bee_cells[neighbourSelectedCellIndex];
        neighbourCell.nextCell = sellected_bee_cell;
        sellected_bee_cell.prevCell = prevCell;
    }

    check_win(null);
}

function checkNeighbourCells(selectedCellIndex:uint):int {
    // Check neighbour cells. Are there any selected adjoining cell?
    // If there is any selected cell return its index
    return <selected cell index>;
    // If there is no selected cell return -1
    return -1;
}

3) Rewrite the check_win method:

// You make call `hitTestObject` method
var hasTop = false;
var hasBottom = false;

var prevCell = enemy1;
do {
    if (prevCell.index < 7) {
        hasTop = true;
    } else if (prevCell.index > 42) {
        hasBottom = true;
    }

    prevCell = prevCell.prevCell;
} while (!prevCell)

var nextCell = enemy1;
do {
    if (nextCell.index < 7) {
        hasTop = true;
    } else if (nextCell.index > 42) {
        hasBottom = true;
    }

    nextCell = nextCell.nextCell;
} while (!nextCell)

if (hasTop && hasBottom) {
    trace("You win!");
}


问:
merge two object arrays with Angular 2 and TypeScript?
I have gone across the JavaScript questions on this topic, this question is specifically about Angular2 with TypeScript.

What I am trying to do is to concatenate the json objects to an array.

My code looks something like this,

```<code>public results: [];

public getResults(){
    this._service.get_search_results(this._slug, this._next).subscribe(
            data => {
                this.results.concat(data.results);
                this._next = data.next;
            },
            err => {
                console.log(err);
            }
        );
}
</code>```

How can I concatenate data.results to this.results with typescript and  angular?

this._slug and this._next are set on class.

thanks.

答:
try this

```<code>data => {
    this.results = [...this.results, ...data.results];
    this._next = data.next;
}
</code>```

Body:
I have gone across the JavaScript questions on this topic, this question is specifically about Angular2 with TypeScript.

What I am trying to do is to concatenate the json objects to an array.

My code looks something like this,

public results: [];

public getResults(){
    this._service.get_search_results(this._slug, this._next).subscribe(
            data => {
                this.results.concat(data.results);
                this._next = data.next;
            },
            err => {
                console.log(err);
            }
        );
}

How can I concatenate data.results to this.results with typescript and  angular?

this._slug and this._next are set on class.

thanks.

Body:
try this

data => {
    this.results = [...this.results, ...data.results];
    this._next = data.next;
}